@syncfusion/ej2-querybuilder 24.2.8 → 25.1.35

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 (58) hide show
  1. package/CHANGELOG.md +18 -0
  2. package/dist/ej2-querybuilder.min.js +2 -2
  3. package/dist/ej2-querybuilder.umd.min.js +2 -2
  4. package/dist/ej2-querybuilder.umd.min.js.map +1 -1
  5. package/dist/es6/ej2-querybuilder.es2015.js +1615 -157
  6. package/dist/es6/ej2-querybuilder.es2015.js.map +1 -1
  7. package/dist/es6/ej2-querybuilder.es5.js +1617 -157
  8. package/dist/es6/ej2-querybuilder.es5.js.map +1 -1
  9. package/dist/global/ej2-querybuilder.min.js +2 -2
  10. package/dist/global/ej2-querybuilder.min.js.map +1 -1
  11. package/dist/global/index.d.ts +1 -1
  12. package/package.json +12 -12
  13. package/src/global.js +2 -0
  14. package/src/query-builder/index.d.ts +1 -0
  15. package/src/query-builder/index.js +1 -0
  16. package/src/query-builder/query-builder-model.d.ts +69 -1
  17. package/src/query-builder/query-builder.d.ts +189 -4
  18. package/src/query-builder/query-builder.js +903 -130
  19. package/src/query-builder/query-library.d.ts +24 -0
  20. package/src/query-builder/query-library.js +689 -0
  21. package/styles/bootstrap-dark.css +29 -12
  22. package/styles/bootstrap.css +29 -12
  23. package/styles/bootstrap4.css +25 -12
  24. package/styles/bootstrap5-dark.css +35 -11
  25. package/styles/bootstrap5.css +35 -11
  26. package/styles/fabric-dark.css +25 -12
  27. package/styles/fabric.css +25 -12
  28. package/styles/fluent-dark.css +39 -11
  29. package/styles/fluent.css +39 -11
  30. package/styles/highcontrast-light.css +25 -12
  31. package/styles/highcontrast.css +25 -12
  32. package/styles/material-dark.css +25 -12
  33. package/styles/material.css +25 -12
  34. package/styles/material3-dark.css +25 -12
  35. package/styles/material3.css +25 -12
  36. package/styles/query-builder/_bds-definition.scss +107 -0
  37. package/styles/query-builder/_layout.scss +37 -7
  38. package/styles/query-builder/_theme.scss +16 -1
  39. package/styles/query-builder/bootstrap-dark.css +29 -12
  40. package/styles/query-builder/bootstrap.css +29 -12
  41. package/styles/query-builder/bootstrap4.css +25 -12
  42. package/styles/query-builder/bootstrap5-dark.css +35 -11
  43. package/styles/query-builder/bootstrap5.css +35 -11
  44. package/styles/query-builder/fabric-dark.css +25 -12
  45. package/styles/query-builder/fabric.css +25 -12
  46. package/styles/query-builder/fluent-dark.css +39 -11
  47. package/styles/query-builder/fluent.css +39 -11
  48. package/styles/query-builder/highcontrast-light.css +25 -12
  49. package/styles/query-builder/highcontrast.css +25 -12
  50. package/styles/query-builder/icons/_bds.scss +7 -0
  51. package/styles/query-builder/material-dark.css +25 -12
  52. package/styles/query-builder/material.css +25 -12
  53. package/styles/query-builder/material3-dark.css +25 -12
  54. package/styles/query-builder/material3.css +25 -12
  55. package/styles/query-builder/tailwind-dark.css +30 -11
  56. package/styles/query-builder/tailwind.css +30 -11
  57. package/styles/tailwind-dark.css +30 -11
  58. package/styles/tailwind.css +30 -11
@@ -89,6 +89,9 @@ __decorate([
89
89
  __decorate([
90
90
  Property(false)
91
91
  ], Rule.prototype, "not", void 0);
92
+ __decorate([
93
+ Property(false)
94
+ ], Rule.prototype, "isLocked", void 0);
92
95
  /**
93
96
  * Defines the property for value.
94
97
  */
@@ -114,6 +117,18 @@ __decorate([
114
117
  */
115
118
  class ShowButtons extends ChildProperty {
116
119
  }
120
+ __decorate([
121
+ Property(false)
122
+ ], ShowButtons.prototype, "cloneRule", void 0);
123
+ __decorate([
124
+ Property(false)
125
+ ], ShowButtons.prototype, "cloneGroup", void 0);
126
+ __decorate([
127
+ Property(false)
128
+ ], ShowButtons.prototype, "lockRule", void 0);
129
+ __decorate([
130
+ Property(false)
131
+ ], ShowButtons.prototype, "lockGroup", void 0);
117
132
  __decorate([
118
133
  Property(true)
119
134
  ], ShowButtons.prototype, "ruleDelete", void 0);
@@ -128,7 +143,7 @@ let QueryBuilder = class QueryBuilder extends Component {
128
143
  super(options, element);
129
144
  this.isReadonly = true;
130
145
  this.fields = { text: 'label', value: 'field' };
131
- this.updatedRule = { not: false, condition: 'and' };
146
+ this.updatedRule = { not: false, condition: 'and', isLocked: false };
132
147
  this.isLocale = false;
133
148
  this.isRefreshed = false;
134
149
  this.isNotified = false;
@@ -139,6 +154,14 @@ let QueryBuilder = class QueryBuilder extends Component {
139
154
  this.isDestroy = false;
140
155
  this.isGetNestedData = false;
141
156
  this.isCustomOprCols = [];
157
+ this.groupCounter = 0;
158
+ this.lockItems = [];
159
+ this.groupIndex = -1;
160
+ this.ruleIndex = -1;
161
+ this.isLastGroup = false;
162
+ this.cloneGrpBtnClick = false;
163
+ this.isMiddleGroup = false;
164
+ this.cloneRuleBtnClick = false;
142
165
  MultiSelect.Inject(CheckBoxSelection);
143
166
  }
144
167
  getPersistData() {
@@ -190,6 +213,14 @@ let QueryBuilder = class QueryBuilder extends Component {
190
213
  getModuleName() {
191
214
  return 'query-builder';
192
215
  }
216
+ requiredModules() {
217
+ const modules = [];
218
+ modules.push({
219
+ member: 'query-library',
220
+ args: [this]
221
+ });
222
+ return modules;
223
+ }
193
224
  GetRootColumnName(field) {
194
225
  return this.separator ? field.split(this.separator)[0] : field;
195
226
  }
@@ -378,31 +409,51 @@ let QueryBuilder = class QueryBuilder extends Component {
378
409
  txtareaElem.style.height = txtareaElem.scrollHeight + 'px';
379
410
  }
380
411
  if (target.tagName === 'BUTTON' && target.className.indexOf('e-qb-toggle') < 0) {
381
- if (target.className.indexOf('e-removerule') > -1) {
382
- this.actionButton = target;
383
- this.deleteRule(target);
384
- }
385
- else if (target.className.indexOf('e-deletegroup') > -1) {
386
- this.actionButton = target;
387
- this.deleteGroup(closest(target, '.e-group-container'));
388
- }
389
- else if (target.className.indexOf('e-edit-rule') > -1) {
390
- const animation = new Animation({ duration: 1000, delay: 0 });
391
- animation.animate('.e-query-builder', { name: 'SlideLeftIn' });
392
- document.getElementById(this.element.id + '_summary_content').style.display = 'none';
393
- if (this.element.querySelectorAll('.e-group-container').length < 1) {
394
- this.addGroupElement(false, this.element, this.rule.condition, false, this.rule.not);
395
- const mRules = extend({}, this.rule, {}, true);
396
- this.setGroupRules(mRules);
397
- this.renderSummaryCollapse();
398
- }
399
- else {
400
- const groupElem = this.element.querySelector('.e-group-container');
401
- if (groupElem.querySelectorAll('.e-collapse-rule').length < 1) {
412
+ switch (true) {
413
+ case target.className.indexOf('e-removerule') > -1:
414
+ this.actionButton = target;
415
+ this.deleteRule(target);
416
+ break;
417
+ case target.className.indexOf('e-clone-rule-btn') > -1:
418
+ this.actionButton = target;
419
+ this.cloneRuleBtnClick = true;
420
+ this.ruleClone(target);
421
+ break;
422
+ case target.className.indexOf('e-lock-rule-btn') > -1:
423
+ this.actionButton = target;
424
+ this.ruleLock(target);
425
+ break;
426
+ case target.className.indexOf('e-lock-grp-btn') > -1:
427
+ this.actionButton = target;
428
+ this.groupLock(target);
429
+ break;
430
+ case target.className.indexOf('e-clone-grp-btn') > -1:
431
+ this.actionButton = target;
432
+ this.cloneGrpBtnClick = true;
433
+ this.groupClone(closest(target, '.e-group-container'));
434
+ break;
435
+ case target.className.indexOf('e-deletegroup') > -1:
436
+ this.actionButton = target;
437
+ this.deleteGroup(closest(target, '.e-group-container'));
438
+ break;
439
+ case target.className.indexOf('e-edit-rule') > -1:
440
+ const animation = new Animation({ duration: 1000, delay: 0 });
441
+ animation.animate('.e-query-builder', { name: 'SlideLeftIn' });
442
+ document.getElementById(this.element.id + '_summary_content').style.display = 'none';
443
+ if (this.element.querySelectorAll('.e-group-container').length < 1) {
444
+ this.addGroupElement(false, this.element, this.rule.condition, false, this.rule.not);
445
+ const mRules = extend({}, this.rule, {}, true);
446
+ this.setGroupRules(mRules);
402
447
  this.renderSummaryCollapse();
403
448
  }
404
- groupElem.style.display = 'block';
405
- }
449
+ else {
450
+ const groupElem = this.element.querySelector('.e-group-container');
451
+ if (groupElem.querySelectorAll('.e-collapse-rule').length < 1) {
452
+ this.renderSummaryCollapse();
453
+ }
454
+ groupElem.style.display = 'block';
455
+ }
456
+ break;
406
457
  }
407
458
  }
408
459
  else if ((target.tagName === 'LABEL' && target.parentElement.className.indexOf('e-btn-group') > -1) ||
@@ -502,7 +553,18 @@ let QueryBuilder = class QueryBuilder extends Component {
502
553
  else {
503
554
  ruleElem = this.createElement('div', { attrs: { class: 'e-rule-container' } });
504
555
  ruleElem.setAttribute('id', target.id + '_rule' + this.ruleIdCounter);
505
- ruleListElem.appendChild(ruleElem);
556
+ if (this.showButtons.cloneRule && this.cloneRuleBtnClick) {
557
+ if (this.ruleIndex < 0) {
558
+ ruleListElem.appendChild(ruleElem);
559
+ }
560
+ else {
561
+ ruleListElem.insertBefore(ruleElem, ruleListElem.children[this.ruleIndex + 1]); // added clone rule to next position
562
+ }
563
+ this.cloneRuleBtnClick = false;
564
+ }
565
+ else {
566
+ ruleListElem.appendChild(ruleElem);
567
+ }
506
568
  this.ruleIdCounter++;
507
569
  }
508
570
  if (column && column.ruleTemplate && rule) {
@@ -552,6 +614,21 @@ let QueryBuilder = class QueryBuilder extends Component {
552
614
  elem = this.ruleElem.querySelector('.e-rule-field').cloneNode(true);
553
615
  ruleElem.appendChild(elem);
554
616
  }
617
+ if (this.showButtons.lockGroup) {
618
+ removeClass(ruleElem.querySelectorAll('.e-lock-grp-btn'), 'e-button-hide');
619
+ }
620
+ if (this.showButtons.lockRule) {
621
+ removeClass(ruleElem.querySelectorAll('.e-lock-rule-btn'), 'e-button-hide');
622
+ }
623
+ if (this.showButtons.cloneGroup) {
624
+ removeClass(ruleElem.querySelectorAll('.e-clone-grp-btn'), 'e-button-hide');
625
+ }
626
+ if (this.showButtons.cloneRule) {
627
+ removeClass(ruleElem.querySelectorAll('.e-clone-rule-btn'), 'e-button-hide');
628
+ }
629
+ if (this.showButtons.ruleDelete) {
630
+ removeClass(ruleElem.querySelectorAll('.e-lock-grp-btn'), 'e-button-hide');
631
+ }
555
632
  if (column && column.ruleTemplate && rule) {
556
633
  this.renderReactTemplates();
557
634
  }
@@ -594,7 +671,7 @@ let QueryBuilder = class QueryBuilder extends Component {
594
671
  else {
595
672
  ruleElem = this.appendRuleElem(trgt, column, act, pId, 'field');
596
673
  ruleElem.querySelector('.e-filter-input').setAttribute('id', ruleElem.id + '_filterkey');
597
- let element = ruleElem.querySelector('button');
674
+ const element = ruleElem.querySelector('.e-rule-delete');
598
675
  if (this.element.className.indexOf('e-device') > -1 || this.displayMode === 'Vertical') {
599
676
  element.textContent = this.l10n.getConstant('Remove');
600
677
  addClass([element], 'e-flat');
@@ -604,8 +681,11 @@ let QueryBuilder = class QueryBuilder extends Component {
604
681
  addClass([element], 'e-round');
605
682
  addClass([element], 'e-icon-btn');
606
683
  element.setAttribute('title', this.l10n.getConstant('DeleteRule'));
607
- element = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-delete-icon' } });
608
- ruleElem.querySelector('button').appendChild(element);
684
+ const spanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-delete-icon' } });
685
+ ruleElem.querySelector('.e-rule-delete').appendChild(spanElement);
686
+ }
687
+ if (!this.showButtons.ruleDelete) {
688
+ element.classList.add('e-button-hide');
609
689
  }
610
690
  }
611
691
  if (this.displayMode === 'Vertical' || this.element.className.indexOf('e-device') > -1) {
@@ -636,6 +716,9 @@ let QueryBuilder = class QueryBuilder extends Component {
636
716
  if (this.separator && rule.field) {
637
717
  ddlValue = this.GetRootColumnName(rule.field);
638
718
  }
719
+ else if (this.autoSelectField) {
720
+ ddlValue = this.GetRootColumnName(rule.field);
721
+ }
639
722
  else {
640
723
  ddlValue = this.isImportRules ? this.GetRootColumnName(rule.field) : rule.field;
641
724
  }
@@ -643,8 +726,7 @@ let QueryBuilder = class QueryBuilder extends Component {
643
726
  dataSource: this.columns,
644
727
  fields: this.fields, placeholder: this.l10n.getConstant('SelectField'),
645
728
  popupHeight: ((this.columns.length > 5) ? height : 'auto'), close: this.fieldClose.bind(this, ruleElem.id + '_filterkey'),
646
- change: this.changeField.bind(this), value: rule ? ddlValue : null, open: this.popupOpen.bind(this, true),
647
- cssClass: 'qb-dropdownlist'
729
+ change: this.changeField.bind(this), value: rule ? ddlValue : null, open: this.popupOpen.bind(this, true), cssClass: 'qb-dropdownlist'
648
730
  };
649
731
  if (this.fieldModel) {
650
732
  ddlField = Object.assign({}, ddlField, this.fieldModel);
@@ -734,12 +816,23 @@ let QueryBuilder = class QueryBuilder extends Component {
734
816
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
735
817
  const custom = rule.custom;
736
818
  if (Object.keys(rule).length) {
737
- rules.rules.push({
738
- 'field': rule.field, 'type': rule.type, 'label': rule.label, 'operator': rule.operator, value: rule.value
739
- });
740
- if (custom) {
741
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
742
- rules.rules[rules.rules.length - 1].custom = custom;
819
+ if (this.ruleIndex < 0) {
820
+ rules.rules.push({
821
+ 'field': rule.field, 'type': rule.type, 'label': rule.label, 'operator': rule.operator, value: rule.value
822
+ });
823
+ if (custom) {
824
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
825
+ rules.rules[rules.rules.length - 1].custom = custom;
826
+ }
827
+ }
828
+ else {
829
+ rules.rules.splice(this.ruleIndex + 1, 0, {
830
+ 'field': rule.field, 'type': rule.type, 'label': rule.label, 'operator': rule.operator, value: rule.value
831
+ });
832
+ if (custom) {
833
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
834
+ rules.rules[this.ruleIndex + 1].custom = custom;
835
+ }
743
836
  }
744
837
  }
745
838
  else {
@@ -747,6 +840,9 @@ let QueryBuilder = class QueryBuilder extends Component {
747
840
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
748
841
  newRule.custom = custom;
749
842
  }
843
+ if (this.autoSelectField) {
844
+ rule.field = newRule.field = this.rule.rules[0].field;
845
+ }
750
846
  rules.rules.push(newRule);
751
847
  }
752
848
  }
@@ -946,6 +1042,8 @@ let QueryBuilder = class QueryBuilder extends Component {
946
1042
  ruleTemplate() {
947
1043
  let tempElem;
948
1044
  let clsName;
1045
+ let cloneClsName;
1046
+ let lockClsName;
949
1047
  const ruleElem = this.createElement('div');
950
1048
  const fieldElem = this.createElement('div', { attrs: { class: 'e-rule-field' } });
951
1049
  tempElem = this.createElement('div', { attrs: { class: 'e-rule-filter' } });
@@ -957,6 +1055,24 @@ let QueryBuilder = class QueryBuilder extends Component {
957
1055
  tempElem = this.createElement('div', { attrs: { class: 'e-rule-value' } });
958
1056
  fieldElem.appendChild(tempElem);
959
1057
  tempElem = this.createElement('div', { attrs: { class: 'e-rule-value-delete' } });
1058
+ if (this.showButtons.cloneRule) {
1059
+ cloneClsName = 'e-clone-rule-btn e-clone-rule e-css e-btn e-small e-round e-icon-btn';
1060
+ }
1061
+ else {
1062
+ cloneClsName = 'e-clone-rule-btn e-clone-rule e-css e-btn e-small e-round e-icon-btn e-button-hide';
1063
+ }
1064
+ if (this.showButtons.lockRule) {
1065
+ lockClsName = 'e-lock-rule-btn e-lock-rule e-css e-btn e-small e-round e-icons e-icon-btn';
1066
+ }
1067
+ else {
1068
+ lockClsName = 'e-lock-rule-btn e-lock-rule e-css e-btn e-small e-round e-icons e-icon-btn e-button-hide';
1069
+ }
1070
+ const cloneRuleBtnElem = this.createElement('button', { attrs: { title: this.l10n.getConstant('CloneRule'), type: 'button', class: cloneClsName } });
1071
+ let spanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-copy' } });
1072
+ cloneRuleBtnElem.appendChild(spanElement);
1073
+ const cloneLockBtnElem = this.createElement('button', { attrs: { title: this.l10n.getConstant('LockRule'), type: 'button', class: lockClsName } });
1074
+ spanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-unlock' } });
1075
+ cloneLockBtnElem.appendChild(spanElement);
960
1076
  if (this.showButtons.ruleDelete || isNullOrUndefined(this.showButtons.ruleDelete)) {
961
1077
  clsName = 'e-removerule e-rule-delete e-css e-btn e-small';
962
1078
  }
@@ -964,6 +1080,8 @@ let QueryBuilder = class QueryBuilder extends Component {
964
1080
  clsName = 'e-removerule e-rule-delete e-css e-btn e-small e-button-hide';
965
1081
  }
966
1082
  const delBtnElem = this.createElement('button', { attrs: { type: 'button', class: clsName } });
1083
+ tempElem.appendChild(cloneRuleBtnElem);
1084
+ tempElem.appendChild(cloneLockBtnElem);
967
1085
  tempElem.appendChild(delBtnElem);
968
1086
  fieldElem.appendChild(tempElem);
969
1087
  ruleElem.appendChild(fieldElem);
@@ -1032,9 +1150,6 @@ let QueryBuilder = class QueryBuilder extends Component {
1032
1150
  button.appendTo(dltGroupBtn);
1033
1151
  dltGroupBtn.setAttribute('title', this.l10n.getConstant('DeleteGroup'));
1034
1152
  rippleEffect(dltGroupBtn, { selector: '.deletegroup' });
1035
- if (!this.headerTemplate) {
1036
- groupElem.querySelector('.e-group-action').appendChild(dltGroupBtn);
1037
- }
1038
1153
  const ruleList = target.querySelector('.e-rule-list');
1039
1154
  const childElems = ruleList.children;
1040
1155
  let grpLen = 0;
@@ -1043,20 +1158,72 @@ let QueryBuilder = class QueryBuilder extends Component {
1043
1158
  grpLen += 1;
1044
1159
  }
1045
1160
  }
1046
- ruleList.appendChild(groupElem);
1161
+ if (this.showButtons.cloneGroup && this.cloneGrpBtnClick) {
1162
+ if (this.groupIndex === (childElems.length - 1)) {
1163
+ ruleList.appendChild(groupElem);
1164
+ this.isLastGroup = true;
1165
+ }
1166
+ else {
1167
+ childElems[this.groupIndex + 1].parentNode.insertBefore(groupElem, childElems[this.groupIndex + 1]); // clone the element to nxt element
1168
+ this.isMiddleGroup = true;
1169
+ }
1170
+ }
1171
+ else {
1172
+ ruleList.appendChild(groupElem);
1173
+ }
1047
1174
  const level = this.levelColl[target.id].slice(0);
1048
1175
  level.push(grpLen);
1049
1176
  this.levelColl[groupElem.id] = level;
1177
+ if (this.groupIndex > -1) {
1178
+ this.refreshLevelColl();
1179
+ }
1050
1180
  if (!this.isImportRules) {
1051
1181
  this.isAddSuccess = true;
1052
1182
  this.addGroups([], target.id.replace(this.element.id + '_', ''));
1053
1183
  this.isAddSuccess = false;
1054
- if (isBtnClick) {
1184
+ if (isBtnClick && this.addRuleToNewGroups) {
1055
1185
  this.addRuleElement(groupElem, {});
1056
1186
  }
1057
1187
  }
1188
+ if (!this.headerTemplate) {
1189
+ let lockClsName = '';
1190
+ if (this.showButtons.cloneGroup) {
1191
+ lockClsName = 'e-clone-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn';
1192
+ }
1193
+ else {
1194
+ lockClsName = 'e-clone-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn e-button-hide';
1195
+ }
1196
+ const cloneBtnElem = this.createElement('button', { attrs: { title: this.l10n.getConstant('CloneGroup'), type: 'button', class: lockClsName } });
1197
+ const spanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-copy' } });
1198
+ cloneBtnElem.appendChild(spanElement);
1199
+ groupElem.querySelector('.e-group-action').appendChild(cloneBtnElem);
1200
+ if (this.showButtons.lockGroup) {
1201
+ lockClsName = 'e-lock-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn';
1202
+ }
1203
+ else {
1204
+ lockClsName = 'e-lock-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn e-button-hide';
1205
+ }
1206
+ const lockBtnElem = this.createElement('button', { attrs: { title: this.l10n.getConstant('LockGroup'), type: 'button', class: lockClsName } });
1207
+ const lockSpanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-unlock' } });
1208
+ lockBtnElem.appendChild(lockSpanElement);
1209
+ groupElem.querySelector('.e-group-action').appendChild(lockBtnElem);
1210
+ groupElem.querySelector('.e-group-action').appendChild(dltGroupBtn);
1211
+ }
1058
1212
  }
1059
1213
  else {
1214
+ if (!this.headerTemplate) {
1215
+ let lockClsName = '';
1216
+ if (this.showButtons.lockGroup) {
1217
+ lockClsName = 'e-lock-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn';
1218
+ }
1219
+ else {
1220
+ lockClsName = 'e-lock-grp-btn e-css e-btn e-small e-round e-icons e-icon-btn e-button-hide';
1221
+ }
1222
+ const lockBtnElem = this.createElement('button', { attrs: { title: this.l10n.getConstant('LockGroup'), type: 'button', class: lockClsName } });
1223
+ const spanElement = this.createElement('span', { attrs: { class: 'e-btn-icon e-icons e-unlock' } });
1224
+ lockBtnElem.appendChild(spanElement);
1225
+ groupElem.querySelector('.e-group-action').appendChild(lockBtnElem);
1226
+ }
1060
1227
  target.appendChild(groupElem);
1061
1228
  this.levelColl[groupElem.id] = [0];
1062
1229
  }
@@ -1313,6 +1480,10 @@ let QueryBuilder = class QueryBuilder extends Component {
1313
1480
  if (this.fieldMode === 'Default') {
1314
1481
  dropDownObj = getComponent(closest(element, '.e-rule-container').querySelector('.e-filter-input'), 'dropdownlist');
1315
1482
  this.selectedColumn = dropDownObj.getDataByValue(dropDownObj.value);
1483
+ if (this.selectedColumn.columns) {
1484
+ dropDownObj = getComponent(closest(element, '.e-rule-container').querySelector('.e-rule-sub-filter .e-dropdownlist'), 'dropdownlist');
1485
+ this.selectedColumn = this.getColumn(dropDownObj.value);
1486
+ }
1316
1487
  }
1317
1488
  else {
1318
1489
  dropDownObj = getComponent(closest(element, '.e-rule-container').querySelector('.e-filter-input'), 'dropdowntree');
@@ -1386,7 +1557,7 @@ let QueryBuilder = class QueryBuilder extends Component {
1386
1557
  this.prevItemData = args.itemData;
1387
1558
  const fieldElem = closest(args.element, '.e-rule-filter') || closest(args.element, '.e-rule-sub-filter');
1388
1559
  const column = this.fieldMode === 'DropdownTree' ? this.getColumn(args.value[0]) : this.getColumn(args.value);
1389
- if (this.fieldMode === 'DropdownTree' && fieldElem != null) {
1560
+ if (this.fieldMode === 'DropdownTree' && fieldElem !== null) {
1390
1561
  const ddtElem = fieldElem.querySelector('.e-dropdowntree.e-control');
1391
1562
  const ddt = getComponent(ddtElem, 'dropdowntree');
1392
1563
  if (column) {
@@ -1458,7 +1629,7 @@ let QueryBuilder = class QueryBuilder extends Component {
1458
1629
  let filterElem = closest(ddlArgs.element, '.e-rule-filter');
1459
1630
  filterElem = filterElem ? filterElem : closest(ddlArgs.element, '.e-rule-sub-filter');
1460
1631
  let ddlObj = getComponent(ddlArgs.element, 'dropdownlist');
1461
- if (this.fieldMode === 'DropdownTree' && filterElem != null) {
1632
+ if (this.fieldMode === 'DropdownTree' && filterElem !== null) {
1462
1633
  ddlObj = getComponent(ddlArgs.element, 'dropdowntree');
1463
1634
  }
1464
1635
  const element = closest(ddlArgs.element, '.e-group-container');
@@ -1585,7 +1756,7 @@ let QueryBuilder = class QueryBuilder extends Component {
1585
1756
  this.GetRootColumnName(rule.field) === this.GetRootColumnName(this.previousColumn.field))) {
1586
1757
  const subField = this.selectedColumn.columns;
1587
1758
  for (let i = 0; i < subField.length; i++) {
1588
- if (rule.field === subField[i].field || rule.field.indexOf(subField[i].field) > -1) {
1759
+ if (rule.field === subField[i].field) {
1589
1760
  dropDownList.value = subField[i].field;
1590
1761
  this.selectedColumn = subField[i];
1591
1762
  subFieldValue = true;
@@ -1624,7 +1795,7 @@ let QueryBuilder = class QueryBuilder extends Component {
1624
1795
  rule.value = [];
1625
1796
  }
1626
1797
  }
1627
- else if (typeof rule.value === 'object' && rule.value != null) {
1798
+ else if (typeof rule.value === 'object' && rule.value !== null) {
1628
1799
  rule.value = rule.value.length > 0 ? rule.value[0] : rule.type === 'number' ? 0 : '';
1629
1800
  }
1630
1801
  if (ddlArgs.previousItemData) {
@@ -1651,6 +1822,9 @@ let QueryBuilder = class QueryBuilder extends Component {
1651
1822
  if (valElem && this.getColumn(rule.field).template) {
1652
1823
  filterElem = operatorElem.previousElementSibling;
1653
1824
  }
1825
+ if (valElem.children.length == 0) {
1826
+ filterElem = operatorElem.previousElementSibling;
1827
+ }
1654
1828
  this.changeRuleValues(filterElem, rule, tempRule, ddlArgs);
1655
1829
  }
1656
1830
  }
@@ -1681,7 +1855,9 @@ let QueryBuilder = class QueryBuilder extends Component {
1681
1855
  tempRule.type = this.fieldMode === 'DropdownTree' ? this.getColumn(fieldObj.value[0]).type :
1682
1856
  this.getColumn(fieldObj.value).type;
1683
1857
  const itemData = ddlArgs.itemData;
1684
- this.renderValues(operatorElem, itemData, ddlArgs.previousItemData, true, rule, tempRule, ddlArgs.element);
1858
+ if (ddlObj.value !== '') {
1859
+ this.renderValues(operatorElem, itemData, ddlArgs.previousItemData, true, rule, tempRule, ddlArgs.element);
1860
+ }
1685
1861
  }
1686
1862
  else {
1687
1863
  const ruleId = closest(operatorElem, '.e-rule-container').id;
@@ -1695,7 +1871,14 @@ let QueryBuilder = class QueryBuilder extends Component {
1695
1871
  }
1696
1872
  const height = (this.element.className.indexOf('e-device') > -1) ? '250px' : '200px';
1697
1873
  let value = operatorList[0].value;
1698
- value = rule ? (rule.operator !== '' ? rule.operator : value) : value;
1874
+ let ddlIdx = 0;
1875
+ if (!this.autoSelectOperator) {
1876
+ value = '';
1877
+ ddlIdx = -1;
1878
+ }
1879
+ if (this.isImportRules || (this.ruleIndex > -1 || this.groupIndex > -1)) {
1880
+ value = rule ? (rule.operator ? rule.operator : value) : value;
1881
+ }
1699
1882
  let ddlOperator;
1700
1883
  ddlOperator = {
1701
1884
  dataSource: operatorList,
@@ -1703,7 +1886,7 @@ let QueryBuilder = class QueryBuilder extends Component {
1703
1886
  placeholder: this.l10n.getConstant('SelectOperator'),
1704
1887
  popupHeight: ((operatorList.length > 5) ? height : 'auto'),
1705
1888
  change: this.changeField.bind(this),
1706
- index: 0,
1889
+ index: ddlIdx,
1707
1890
  value: value,
1708
1891
  open: this.popupOpen.bind(this, false)
1709
1892
  };
@@ -1717,7 +1900,12 @@ let QueryBuilder = class QueryBuilder extends Component {
1717
1900
  tempRule.type = this.selectedColumn.type;
1718
1901
  tempRule.operator = rule.operator;
1719
1902
  }
1720
- this.renderValues(operatorElem, this.selectedColumn, ddlArgs.previousItemData, false, rule, tempRule, ddlArgs.element);
1903
+ if (!isNullOrUndefined(value) && value !== '') {
1904
+ this.renderValues(operatorElem, this.selectedColumn, ddlArgs.previousItemData, false, rule, tempRule, ddlArgs.element);
1905
+ }
1906
+ else if (this.autoSelectField && this.autoSelectOperator) {
1907
+ this.renderValues(operatorElem, this.selectedColumn, ddlArgs.previousItemData, false, rule, tempRule, ddlArgs.element);
1908
+ }
1721
1909
  }
1722
1910
  }
1723
1911
  if (!this.isImportRules) {
@@ -2074,14 +2262,14 @@ let QueryBuilder = class QueryBuilder extends Component {
2074
2262
  const columnData = this.getItemData(parentId);
2075
2263
  let selectedValue;
2076
2264
  const isTemplate = (typeof columnData.template === 'string');
2077
- if (this.isImportRules || this.isPublic || isTemplate) {
2265
+ if (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1 || this.isPublic || isTemplate) {
2078
2266
  selectedValue = rule.value;
2079
2267
  }
2080
2268
  else {
2081
2269
  selectedValue = this.setDefaultValue(parentId, false, false);
2082
2270
  }
2083
2271
  if ((operator === 'in' || operator === 'notin') && (this.dataColl.length || columnData.values)) {
2084
- selectedVal = this.isImportRules ? rule.value : this.setDefaultValue(parentId, true, false);
2272
+ selectedVal = (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1) ? rule.value : this.setDefaultValue(parentId, true, false);
2085
2273
  this.renderMultiSelect(columnData, parentId, idx, selectedVal, columnData.values);
2086
2274
  if (this.displayMode === 'Vertical' || this.element.className.indexOf('e-device') > -1) {
2087
2275
  ruleValElem.style.width = '100%';
@@ -2093,7 +2281,7 @@ let QueryBuilder = class QueryBuilder extends Component {
2093
2281
  }
2094
2282
  else {
2095
2283
  if (operator === 'in' || operator === 'notin') {
2096
- selectedVal = this.isImportRules ? rule.value : this.setDefaultValue(parentId, true, false);
2284
+ selectedVal = (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1) ? rule.value : this.setDefaultValue(parentId, true, false);
2097
2285
  selectedValue = selectedVal.join(',');
2098
2286
  }
2099
2287
  let txtBox;
@@ -2113,9 +2301,9 @@ let QueryBuilder = class QueryBuilder extends Component {
2113
2301
  renderNumberValue(parentId, rule, operator, idx, ruleValElem, itemData, length) {
2114
2302
  const columnData = this.getItemData(parentId);
2115
2303
  const isTemplate = (typeof columnData.template === 'string');
2116
- let selectedVal = (this.isImportRules || this.isPublic || isTemplate) ? rule.value : this.setDefaultValue(parentId, false, true);
2304
+ let selectedVal = (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1 || this.isPublic || isTemplate) ? rule.value : this.setDefaultValue(parentId, false, true);
2117
2305
  if ((operator === 'in' || operator === 'notin') && (this.dataColl.length || columnData.values)) {
2118
- selectedVal = this.isImportRules ? rule.value : this.setDefaultValue(parentId, true, false);
2306
+ selectedVal = (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1) ? rule.value : this.setDefaultValue(parentId, true, false);
2119
2307
  this.renderMultiSelect(columnData, parentId, idx, selectedVal, columnData.values);
2120
2308
  if (this.element.className.indexOf('e-device') > -1 || this.displayMode === 'Vertical') {
2121
2309
  ruleValElem.style.width = '100%';
@@ -2126,7 +2314,7 @@ let QueryBuilder = class QueryBuilder extends Component {
2126
2314
  }
2127
2315
  }
2128
2316
  else if (operator === 'in' || operator === 'notin') {
2129
- selectedVal = this.isImportRules ? rule.value : this.setDefaultValue(parentId, true, false);
2317
+ selectedVal = (this.isImportRules || this.ruleIndex > -1 || this.groupIndex > -1) ? rule.value : this.setDefaultValue(parentId, true, false);
2130
2318
  const selVal = selectedVal.join(',');
2131
2319
  let txtInp;
2132
2320
  txtInp = {
@@ -2399,8 +2587,8 @@ let QueryBuilder = class QueryBuilder extends Component {
2399
2587
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
2400
2588
  : this.getColumn(filtObj.value);
2401
2589
  this.selectedRule = column;
2590
+ const ddlObj = getComponent(target.querySelector('input'), 'dropdownlist');
2402
2591
  if (isRender) {
2403
- const ddlObj = getComponent(target.querySelector('input'), 'dropdownlist');
2404
2592
  itemData = element.id.indexOf('operator') > -1 ? itemData : this.selectedRule;
2405
2593
  if (itemData.operators) {
2406
2594
  ddlObj.value = null;
@@ -2408,7 +2596,13 @@ let QueryBuilder = class QueryBuilder extends Component {
2408
2596
  ddlObj.dataSource = itemData.operators;
2409
2597
  ddlObj.index = this.getOperatorIndex(ddlObj, rule);
2410
2598
  ddlObj.value = tempRule.operator = ddlObj.dataSource[ddlObj.index].value;
2411
- ddlObj.dataBind();
2599
+ if (!this.autoSelectOperator) {
2600
+ ddlObj.index = -1;
2601
+ tempRule.operator = ddlObj.value = '';
2602
+ }
2603
+ else {
2604
+ ddlObj.dataBind();
2605
+ }
2412
2606
  }
2413
2607
  }
2414
2608
  const operator = tempRule.operator.toString();
@@ -2441,39 +2635,41 @@ let QueryBuilder = class QueryBuilder extends Component {
2441
2635
  this.validateValue(rule, closest(target, '.e-rule-container'));
2442
2636
  this.destroyControls(target);
2443
2637
  }
2444
- if (column) {
2445
- itemData.template = column.template;
2446
- }
2447
- if (itemData.template) {
2448
- addClass([target.nextElementSibling], 'e-template-value');
2449
- itemData.template = column.template;
2450
- isTempRendered = this.setColumnTemplate(itemData, parentId, column.field, itemData.value ||
2451
- operator, target, rule);
2452
- }
2453
- if (isTempRendered) {
2454
- const parentElem = target.parentElement.querySelector('.e-rule-value');
2455
- if (this.element.className.indexOf('e-device') > -1 || this.displayMode === 'Vertical') {
2456
- parentElem.style.width = '100%';
2457
- }
2458
- else {
2459
- parentElem.style.width = '200px';
2460
- }
2461
- }
2462
- else {
2463
- removeClass([target.nextElementSibling], 'e-template-value');
2464
- let inputLen = 1;
2465
- if (tempRule.type === 'boolean') {
2466
- inputLen = this.selectedColumn.values ? this.selectedColumn.values.length : 2;
2638
+ if (this.isImportRules || (ddlObj && ddlObj.value !== '')) {
2639
+ if (column) {
2640
+ itemData.template = column.template;
2641
+ }
2642
+ if (itemData.template) {
2643
+ addClass([target.nextElementSibling], 'e-template-value');
2644
+ itemData.template = column.template;
2645
+ isTempRendered = this.setColumnTemplate(itemData, parentId, column.field, itemData.value ||
2646
+ operator, target, rule);
2647
+ }
2648
+ if (isTempRendered) {
2649
+ const parentElem = target.parentElement.querySelector('.e-rule-value');
2650
+ if (this.element.className.indexOf('e-device') > -1 || this.displayMode === 'Vertical') {
2651
+ parentElem.style.width = '100%';
2652
+ }
2653
+ else {
2654
+ parentElem.style.width = '200px';
2655
+ }
2467
2656
  }
2468
2657
  else {
2469
- inputLen = (operator && operator.toLowerCase().indexOf('between') > -1) ? 2 : 1;
2470
- }
2471
- for (let i = 0; i < inputLen; i++) {
2472
- const valElem = this.createElement('input', { attrs: { type: 'text', id: parentId + '_valuekey' + i } });
2473
- target.nextElementSibling.appendChild(valElem);
2658
+ removeClass([target.nextElementSibling], 'e-template-value');
2659
+ let inputLen = 1;
2660
+ if (tempRule.type === 'boolean') {
2661
+ inputLen = this.selectedColumn.values ? this.selectedColumn.values.length : 2;
2662
+ }
2663
+ else {
2664
+ inputLen = (operator && operator.toLowerCase().indexOf('between') > -1) ? 2 : 1;
2665
+ }
2666
+ for (let i = 0; i < inputLen; i++) {
2667
+ const valElem = this.createElement('input', { attrs: { type: 'text', id: parentId + '_valuekey' + i } });
2668
+ target.nextElementSibling.appendChild(valElem);
2669
+ }
2474
2670
  }
2671
+ this.renderControls(target, itemData, rule, tempRule, isTempRendered);
2475
2672
  }
2476
- this.renderControls(target, itemData, rule, tempRule, isTempRendered);
2477
2673
  }
2478
2674
  else {
2479
2675
  const parentElem = target.parentElement.querySelector('.e-rule-value');
@@ -2906,8 +3102,8 @@ let QueryBuilder = class QueryBuilder extends Component {
2906
3102
  let i;
2907
3103
  let len;
2908
3104
  let tooltip;
2909
- let popupElement;
2910
3105
  super.destroy();
3106
+ let popupElement;
2911
3107
  element = this.element.querySelectorAll('.e-addrulegroup');
2912
3108
  len = element.length;
2913
3109
  for (i = 0; i < len; i++) {
@@ -2993,7 +3189,8 @@ let QueryBuilder = class QueryBuilder extends Component {
2993
3189
  if (grouplen) {
2994
3190
  this.isPublic = true;
2995
3191
  for (let i = 0, len = groups.length; i < len; i++) {
2996
- this.updatedRule = { condition: groups[i].condition, not: groups[i].not };
3192
+ this.updatedRule = { isLocked: groups[i].isLocked, condition: groups[i].condition,
3193
+ not: groups[i].not };
2997
3194
  this.importRules(groups[i], groupElem, false, groups[i].not);
2998
3195
  }
2999
3196
  this.isPublic = false;
@@ -3001,15 +3198,27 @@ let QueryBuilder = class QueryBuilder extends Component {
3001
3198
  else {
3002
3199
  let condition = 'and';
3003
3200
  let not = false;
3201
+ let isLocked = false;
3004
3202
  if (this.updatedRule) {
3005
3203
  condition = this.updatedRule.condition;
3006
3204
  not = this.updatedRule.not;
3205
+ isLocked = this.updatedRule.isLocked;
3007
3206
  }
3008
- if (this.enableNotCondition) {
3009
- rule.rules.push({ 'condition': condition, 'not': not, rules: [] });
3207
+ if (this.groupIndex < 0) {
3208
+ if (this.enableNotCondition) {
3209
+ rule.rules.push({ 'condition': condition, 'not': not, rules: [] });
3210
+ }
3211
+ else {
3212
+ rule.rules.push({ 'condition': condition, rules: [] });
3213
+ }
3010
3214
  }
3011
3215
  else {
3012
- rule.rules.push({ 'condition': condition, rules: [] });
3216
+ if (this.enableNotCondition) {
3217
+ rule.rules.splice(this.groupIndex + 1, 0, { condition: condition, not: not, rules: [], isLocked: isLocked });
3218
+ }
3219
+ else {
3220
+ rule.rules.splice(this.groupIndex + 1, 0, { condition: condition, rules: [], isLocked: isLocked });
3221
+ }
3013
3222
  }
3014
3223
  }
3015
3224
  if (!this.headerTemplate) {
@@ -3191,17 +3400,53 @@ let QueryBuilder = class QueryBuilder extends Component {
3191
3400
  this.refresh();
3192
3401
  break;
3193
3402
  case 'showButtons':
3194
- if (newProp.showButtons.ruleDelete) {
3195
- removeClass(this.element.querySelectorAll('.e-rule-delete'), 'e-button-hide');
3403
+ if (!isNullOrUndefined(newProp.showButtons.lockGroup)) {
3404
+ if (newProp.showButtons.lockGroup) {
3405
+ removeClass(this.element.querySelectorAll('.e-lock-grp-btn'), 'e-button-hide');
3406
+ }
3407
+ else {
3408
+ addClass(this.element.querySelectorAll('.e-lock-grp-btn'), 'e-button-hide');
3409
+ }
3196
3410
  }
3197
- else {
3198
- addClass(this.element.querySelectorAll('.e-rule-delete'), 'e-button-hide');
3411
+ if (!isNullOrUndefined(newProp.showButtons.lockRule)) {
3412
+ if (newProp.showButtons.lockRule) {
3413
+ removeClass(this.element.querySelectorAll('.e-lock-rule-btn'), 'e-button-hide');
3414
+ }
3415
+ else {
3416
+ addClass(this.element.querySelectorAll('.e-lock-rule-btn'), 'e-button-hide');
3417
+ }
3199
3418
  }
3200
- if (newProp.showButtons.groupDelete) {
3201
- removeClass(this.element.querySelectorAll('.e-deletegroup'), 'e-button-hide');
3419
+ if (!isNullOrUndefined(newProp.showButtons.cloneGroup)) {
3420
+ if (newProp.showButtons.cloneGroup) {
3421
+ removeClass(this.element.querySelectorAll('.e-clone-grp-btn'), 'e-button-hide');
3422
+ }
3423
+ else {
3424
+ addClass(this.element.querySelectorAll('.e-clone-grp-btn'), 'e-button-hide');
3425
+ }
3202
3426
  }
3203
- else {
3204
- addClass(this.element.querySelectorAll('.e-deletegroup'), 'e-button-hide');
3427
+ if (!isNullOrUndefined(newProp.showButtons.cloneRule)) {
3428
+ if (newProp.showButtons.cloneRule) {
3429
+ removeClass(this.element.querySelectorAll('.e-clone-rule-btn'), 'e-button-hide');
3430
+ }
3431
+ else {
3432
+ addClass(this.element.querySelectorAll('.e-clone-rule-btn'), 'e-button-hide');
3433
+ }
3434
+ }
3435
+ if (!isNullOrUndefined(newProp.showButtons.ruleDelete)) {
3436
+ if (newProp.showButtons.ruleDelete) {
3437
+ removeClass(this.element.querySelectorAll('.e-rule-delete'), 'e-button-hide');
3438
+ }
3439
+ else {
3440
+ addClass(this.element.querySelectorAll('.e-rule-delete'), 'e-button-hide');
3441
+ }
3442
+ }
3443
+ if (!isNullOrUndefined(newProp.showButtons.groupDelete)) {
3444
+ if (newProp.showButtons.groupDelete) {
3445
+ removeClass(this.element.querySelectorAll('.e-deletegroup'), 'e-button-hide');
3446
+ }
3447
+ else {
3448
+ addClass(this.element.querySelectorAll('.e-deletegroup'), 'e-button-hide');
3449
+ }
3205
3450
  }
3206
3451
  break;
3207
3452
  case 'cssClass':
@@ -3278,8 +3523,11 @@ let QueryBuilder = class QueryBuilder extends Component {
3278
3523
  this.element.id = this.element.id || getUniqueID('ej2-querybuilder');
3279
3524
  this.defaultLocale = {
3280
3525
  StartsWith: 'Starts With',
3526
+ DoesNotStartWith: 'Does Not Start With',
3281
3527
  EndsWith: 'Ends With',
3528
+ DoesNotEndWith: 'Does Not End With',
3282
3529
  Contains: 'Contains',
3530
+ DoesNotContain: 'Does Not Contain',
3283
3531
  NotLike: 'Not Like',
3284
3532
  Like: 'Like',
3285
3533
  Equal: 'Equal',
@@ -3313,7 +3561,13 @@ let QueryBuilder = class QueryBuilder extends Component {
3313
3561
  IsNotNull: 'Is Not Null',
3314
3562
  True: 'true',
3315
3563
  False: 'false',
3316
- AddButton: 'Add Group/Condition'
3564
+ AddButton: 'Add Group/Condition',
3565
+ CloneGroup: 'Clone Group',
3566
+ LockGroup: 'Lock Group',
3567
+ CloneRule: 'Clone Rule',
3568
+ LockRule: 'Lock Rule',
3569
+ UnlockRule: 'Unlock Rule',
3570
+ UnlockGroup: 'Unlock Group'
3317
3571
  };
3318
3572
  this.l10n = new L10n('querybuilder', this.defaultLocale, this.locale);
3319
3573
  this.intl = new Internationalization(this.locale);
@@ -3326,8 +3580,11 @@ let QueryBuilder = class QueryBuilder extends Component {
3326
3580
  this.customOperators = {
3327
3581
  stringOperator: [
3328
3582
  { value: 'startswith', key: this.l10n.getConstant('StartsWith') },
3583
+ { value: 'notstartswith', key: this.l10n.getConstant('DoesNotStartWith') },
3329
3584
  { value: 'endswith', key: this.l10n.getConstant('EndsWith') },
3585
+ { value: 'notendswith', key: this.l10n.getConstant('DoesNotEndWith') },
3330
3586
  { value: 'contains', key: this.l10n.getConstant('Contains') },
3587
+ { value: 'notcontains', key: this.l10n.getConstant('DoesNotContain') },
3331
3588
  { value: 'equal', key: this.l10n.getConstant('Equal') },
3332
3589
  { value: 'notequal', key: this.l10n.getConstant('NotEqual') },
3333
3590
  { value: 'in', key: this.l10n.getConstant('In') },
@@ -3341,7 +3598,9 @@ let QueryBuilder = class QueryBuilder extends Component {
3341
3598
  { value: 'greaterthanorequal', key: this.l10n.getConstant('GreaterThanOrEqual') },
3342
3599
  { value: 'lessthan', key: this.l10n.getConstant('LessThan') },
3343
3600
  { value: 'lessthanorequal', key: this.l10n.getConstant('LessThanOrEqual') },
3344
- { value: 'notequal', key: this.l10n.getConstant('NotEqual') }
3601
+ { value: 'notequal', key: this.l10n.getConstant('NotEqual') },
3602
+ { value: 'between', key: this.l10n.getConstant('Between') },
3603
+ { value: 'notbetween', key: this.l10n.getConstant('NotBetween') }
3345
3604
  ],
3346
3605
  booleanOperator: [
3347
3606
  { value: 'equal', key: this.l10n.getConstant('Equal') },
@@ -3642,6 +3901,10 @@ let QueryBuilder = class QueryBuilder extends Component {
3642
3901
  if (!(rule.rules[0] && rule.rules[0].rules)) {
3643
3902
  this.disableRuleCondition(groupElem, rule);
3644
3903
  }
3904
+ const tooltipElem = this.element.querySelectorAll('.e-tooltip');
3905
+ for (let i = 0; i < tooltipElem.length; i++) {
3906
+ getComponent(tooltipElem[i], 'tooltip').refresh(tooltipElem[i]);
3907
+ }
3645
3908
  if (!this.isImportRules) {
3646
3909
  this.trigger('change', args);
3647
3910
  }
@@ -3659,6 +3922,10 @@ let QueryBuilder = class QueryBuilder extends Component {
3659
3922
  this.setProperties({ rule: rule }, true);
3660
3923
  rule = this.getRuleCollection(this.rule, false);
3661
3924
  this.importRules(this.rule, this.element.querySelector('.e-group-container'), true, this.rule.not, isRoot);
3925
+ if (rule.isLocked) {
3926
+ const lockGrpTarget = this.element.querySelector('.e-group-container').querySelector('.e-lock-grp-btn');
3927
+ this.groupLock(lockGrpTarget);
3928
+ }
3662
3929
  this.isImportRules = false;
3663
3930
  }
3664
3931
  keyBoardHandler(e) {
@@ -3754,7 +4021,8 @@ let QueryBuilder = class QueryBuilder extends Component {
3754
4021
  rule.value !== undefined)) || (customObj && customObj.isQuestion)) {
3755
4022
  const condition = rule.condition;
3756
4023
  rule = {
3757
- 'label': rule.label, 'field': rule.field, 'operator': rule.operator, 'type': rule.type, 'value': rule.value
4024
+ 'label': rule.label, 'field': rule.field, 'operator': rule.operator, 'type': rule.type, 'value': rule.value,
4025
+ 'isLocked': rule.isLocked
3758
4026
  };
3759
4027
  if (condition) {
3760
4028
  rule.condition = condition;
@@ -3763,6 +4031,7 @@ let QueryBuilder = class QueryBuilder extends Component {
3763
4031
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
3764
4032
  rule.custom = customObj;
3765
4033
  }
4034
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
3766
4035
  if ((rule.operator === 'in' || rule.operator === 'notin') && rule.value && rule.value.length === 0) {
3767
4036
  rule = {};
3768
4037
  }
@@ -3788,10 +4057,10 @@ let QueryBuilder = class QueryBuilder extends Component {
3788
4057
  }
3789
4058
  else {
3790
4059
  if (this.enableNotCondition) {
3791
- rule = { 'condition': rule.condition, 'rules': rule.rules, 'not': rule.not };
4060
+ rule = { 'condition': rule.condition, 'rules': rule.rules, 'not': rule.not, 'isLocked': rule.isLocked };
3792
4061
  }
3793
4062
  else {
3794
- rule = { 'condition': rule.condition, 'rules': rule.rules };
4063
+ rule = { 'condition': rule.condition, 'rules': rule.rules, 'isLocked': rule.isLocked };
3795
4064
  }
3796
4065
  if (customObj) {
3797
4066
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
@@ -3956,11 +4225,20 @@ let QueryBuilder = class QueryBuilder extends Component {
3956
4225
  let ruleValue;
3957
4226
  let ignoreCase = false;
3958
4227
  let column;
3959
- const ignoreOper = ['notcontains', 'notstartswith', 'notendswith'];
3960
4228
  if (!ruleColl) {
3961
4229
  return pred;
3962
4230
  }
3963
4231
  for (let i = 0, len = ruleColl.length; i < len; i++) {
4232
+ let operator = ruleColl[i].operator;
4233
+ if (operator === 'notstartswith') {
4234
+ operator = 'doesnotstartwith';
4235
+ }
4236
+ else if (operator === 'notendswith') {
4237
+ operator = 'doesnotendwith';
4238
+ }
4239
+ else if (operator === 'notcontains') {
4240
+ operator = 'doesnotcontain';
4241
+ }
3964
4242
  const keys = Object.keys(ruleColl[i]);
3965
4243
  ignoreCase = false;
3966
4244
  if (keys.indexOf('rules') > -1 && ruleColl[i].rules) {
@@ -3979,7 +4257,7 @@ let QueryBuilder = class QueryBuilder extends Component {
3979
4257
  }
3980
4258
  }
3981
4259
  }
3982
- else if (!isNullOrUndefined(ruleColl[i].operator) && !isNullOrUndefined(ruleColl[i].operator.length)) {
4260
+ else if (!isNullOrUndefined(operator) && !isNullOrUndefined(operator.length)) {
3983
4261
  const oper = ruleColl[i].operator.toLowerCase();
3984
4262
  let isDateFilter = false;
3985
4263
  const dateOperColl = ['equal', 'notequal', 'greaterthan', 'greaterthanorequal', 'lessthan', 'lessthanorequal'];
@@ -4010,23 +4288,20 @@ let QueryBuilder = class QueryBuilder extends Component {
4010
4288
  }
4011
4289
  if (i === 0) {
4012
4290
  if (isDateFilter || (oper.indexOf('in') > -1 || oper.indexOf('between') > -1 || oper.indexOf('null') > -1 ||
4013
- oper.indexOf('empty') > -1) && oper.indexOf('contains') < 0) {
4291
+ oper.indexOf('empty') > -1) && (oper.indexOf('contain') < 0)) {
4014
4292
  pred = isDateFilter ? this.datePredicate(ruleColl[i], ruleValue) :
4015
4293
  this.arrayPredicate(ruleColl[i]);
4016
4294
  }
4017
4295
  else {
4018
4296
  const value = ruleValue;
4019
- if (value !== '' && ignoreOper.indexOf(oper) < 0) {
4020
- pred = new Predicate(ruleColl[i].field, ruleColl[i].operator, ruleValue, ignoreCase);
4297
+ if (value !== '') {
4298
+ pred = new Predicate(ruleColl[i].field, operator, ruleValue, ignoreCase);
4021
4299
  }
4022
4300
  }
4023
4301
  }
4024
4302
  else {
4025
- if (ignoreOper.indexOf(oper) > -1) {
4026
- continue;
4027
- }
4028
4303
  if (isDateFilter || (oper.indexOf('in') > -1 || oper.indexOf('between') > -1 ||
4029
- oper.indexOf('null') > -1 || oper.indexOf('empty') > -1) && oper.indexOf('contains') < 0) {
4304
+ oper.indexOf('null') > -1 || oper.indexOf('empty') > -1) && oper.indexOf('contain') < 0) {
4030
4305
  pred = isDateFilter ? this.datePredicate(ruleColl[i], ruleValue, pred, rule.condition) :
4031
4306
  this.arrayPredicate(ruleColl[i], pred, rule.condition);
4032
4307
  }
@@ -4035,19 +4310,19 @@ let QueryBuilder = class QueryBuilder extends Component {
4035
4310
  const value = ruleValue;
4036
4311
  if (pred && value !== '') {
4037
4312
  pred
4038
- = pred.and(ruleColl[i].field, ruleColl[i].operator, ruleValue, ignoreCase);
4313
+ = pred.and(ruleColl[i].field, operator, ruleValue, ignoreCase);
4039
4314
  }
4040
4315
  else if (value !== '') {
4041
- pred = new Predicate(ruleColl[i].field, ruleColl[i].operator, ruleValue, ignoreCase);
4316
+ pred = new Predicate(ruleColl[i].field, operator, ruleValue, ignoreCase);
4042
4317
  }
4043
4318
  }
4044
4319
  else {
4045
4320
  const value = ruleValue;
4046
4321
  if (pred && value !== '') {
4047
- pred = pred.or(ruleColl[i].field, ruleColl[i].operator, ruleValue, ignoreCase);
4322
+ pred = pred.or(ruleColl[i].field, operator, ruleValue, ignoreCase);
4048
4323
  }
4049
4324
  else if (value !== '') {
4050
- pred = new Predicate(ruleColl[i].field, ruleColl[i].operator, ruleValue, ignoreCase);
4325
+ pred = new Predicate(ruleColl[i].field, operator, ruleValue, ignoreCase);
4051
4326
  }
4052
4327
  }
4053
4328
  }
@@ -4327,15 +4602,28 @@ let QueryBuilder = class QueryBuilder extends Component {
4327
4602
  for (let i = 0, len = ruleColl.length; i < len; i++) {
4328
4603
  const keys = Object.keys(ruleColl[i]);
4329
4604
  if (!isNullOrUndefined(ruleColl[i].rules) && keys.indexOf('rules') > -1 && (ruleColl[i].rules.length !== 0)) {
4605
+ if (this.element.querySelectorAll('.e-group-container').length > this.maxGroupCount) {
4606
+ return null;
4607
+ }
4330
4608
  parentElem = this.renderGroup(ruleColl[i], ruleColl[i].condition, parentElem, ruleColl[i].not);
4331
4609
  parentElem = this.importRules(ruleColl[i], parentElem, true);
4332
4610
  }
4333
4611
  else {
4334
4612
  this.renderRule(ruleColl[i], parentElem);
4335
4613
  }
4614
+ if (!isNullOrUndefined(ruleColl[i].rules) && ruleColl[i].isLocked) {
4615
+ const lockGrpTarget = parentElem.querySelector('.e-rule-list').children[i].querySelector('.e-lock-grp-btn');
4616
+ this.groupLock(lockGrpTarget);
4617
+ }
4618
+ if (isNullOrUndefined(ruleColl[i].rules) && ruleColl[i].isLocked) {
4619
+ const lockRuleTarget = parentElem.querySelector('.e-rule-list').children[i].querySelector('.e-lock-rule-btn');
4620
+ this.ruleLock(lockRuleTarget);
4621
+ }
4336
4622
  }
4337
4623
  }
4338
- parentElem = closest(parentElem, '.e-rule-list');
4624
+ if (parentElem) {
4625
+ parentElem = closest(parentElem, '.e-rule-list');
4626
+ }
4339
4627
  if (parentElem) {
4340
4628
  parentElem = closest(parentElem, '.e-group-container');
4341
4629
  }
@@ -4344,7 +4632,20 @@ let QueryBuilder = class QueryBuilder extends Component {
4344
4632
  renderGroup(rule, condition, parentElem, not, isRoot) {
4345
4633
  this.addGroupElement(true, parentElem, condition, false, not, isRoot, rule); //Child group
4346
4634
  const element = parentElem.querySelectorAll('.e-group-container');
4347
- return element[element.length - 1];
4635
+ const cloneElem = parentElem.querySelector('.e-rule-list').children;
4636
+ if (this.showButtons.cloneGroup && this.cloneGrpBtnClick && this.isMiddleGroup) {
4637
+ this.isMiddleGroup = false;
4638
+ this.cloneGrpBtnClick = false;
4639
+ return cloneElem[this.groupIndex + 1]; // group added in the middle
4640
+ }
4641
+ else if (this.showButtons.cloneGroup && this.cloneGrpBtnClick && this.isLastGroup) {
4642
+ this.isLastGroup = false;
4643
+ this.cloneGrpBtnClick = false;
4644
+ return cloneElem[cloneElem.length - 1]; // group added in the end
4645
+ }
4646
+ else {
4647
+ return element[element.length - 1];
4648
+ }
4348
4649
  }
4349
4650
  renderRule(rule, parentElem) {
4350
4651
  if (parentElem.className.indexOf('e-group-container') > -1) {
@@ -4542,15 +4843,19 @@ let QueryBuilder = class QueryBuilder extends Component {
4542
4843
  valueStr += rule.value ? '("%' + rule.value + '%")' : '(' + rule.value + ')';
4543
4844
  }
4544
4845
  else {
4545
- if (rule.type === 'number' || typeof rule.value === 'boolean' || rule.value === null) {
4846
+ if (rule.type === 'number' || typeof rule.value === 'boolean' ||
4847
+ (rule.value === null && (rule.operator.toString().indexOf('empty') < -1))) {
4546
4848
  valueStr += rule.value;
4547
4849
  }
4850
+ else if (rule.operator.toString().indexOf('empty') > -1) {
4851
+ valueStr += '""';
4852
+ }
4548
4853
  else {
4549
4854
  valueStr += '"' + rule.value + '"';
4550
4855
  }
4551
4856
  }
4552
4857
  }
4553
- if (rule.operator.toString().indexOf('null') > -1 || (rule.operator.toString().indexOf('empty') > -1)) {
4858
+ if (rule.operator.toString().indexOf('null') > -1) {
4554
4859
  if (enableEscape) {
4555
4860
  rule.field = '`' + rule.field + '`';
4556
4861
  }
@@ -4562,6 +4867,13 @@ let QueryBuilder = class QueryBuilder extends Component {
4562
4867
  queryStr += rule.field + ' ' + ruleOpertor;
4563
4868
  }
4564
4869
  else {
4870
+ let custOper = ruleOpertor;
4871
+ if (rule.operator === 'isempty') {
4872
+ custOper = '=';
4873
+ }
4874
+ else if (rule.operator === 'isnotempty') {
4875
+ custOper = '!=';
4876
+ }
4565
4877
  if (enableEscape) {
4566
4878
  rule.field = '`' + rule.field + '`';
4567
4879
  }
@@ -4570,7 +4882,7 @@ let QueryBuilder = class QueryBuilder extends Component {
4570
4882
  rule.field = '"' + rule.field + '"';
4571
4883
  }
4572
4884
  }
4573
- queryStr += rule.field + ' ' + ruleOpertor + ' ' + valueStr;
4885
+ queryStr += rule.field + ' ' + custOper + ' ' + valueStr;
4574
4886
  }
4575
4887
  if (rule.condition && rule.condition !== '') {
4576
4888
  condition = rule.condition;
@@ -4600,7 +4912,7 @@ let QueryBuilder = class QueryBuilder extends Component {
4600
4912
  * Sets the rules from the sql query.
4601
4913
  *
4602
4914
  * @param {string} sqlString - 'sql String' to be passed to set the rule.
4603
- * @param {boolean} sqlLocale - Set `true` if Localization for Sql query.
4915
+ * @param {boolean} sqlLocale - Optional. Set `true` if Localization for Sql query.
4604
4916
  * @returns {void}
4605
4917
  */
4606
4918
  setRulesFromSql(sqlString, sqlLocale) {
@@ -4632,15 +4944,163 @@ let QueryBuilder = class QueryBuilder extends Component {
4632
4944
  *
4633
4945
  * @param {RuleModel} rule - 'rule' to be passed to get the sql.
4634
4946
  * @param {boolean} allowEscape - Set `true` if it exclude the escape character.
4635
- * @param {boolean} sqlLocale - Set `true` if Localization for Sql query.
4636
- * @returns {object} - Sql query from rules.
4947
+ * @param {boolean} sqlLocale - Set `true` if Localization for Sql query.
4948
+ * @returns {string} - Sql query from rules.
4637
4949
  */
4638
4950
  getSqlFromRules(rule, allowEscape, sqlLocale) {
4639
4951
  if (!rule) {
4640
4952
  rule = this.getValidRules();
4641
4953
  }
4642
4954
  rule = this.getRuleCollection(rule, false);
4643
- return this.getSqlString(this.getValidRules(rule), allowEscape, null, sqlLocale).replace(/"/g, '\'');
4955
+ const sqlString = this.getSqlString(this.getValidRules(rule), allowEscape, null, sqlLocale).replace(/"/g, '\'');
4956
+ return sqlString;
4957
+ }
4958
+ /**
4959
+ * Gets the parameter SQL query from rules.
4960
+ *
4961
+ * @param {RuleModel} rule – Specify the rule to be passed to get the parameter sql string.
4962
+ * @returns {ParameterizedSql} – Parameterized SQL query from rules.
4963
+ */
4964
+ getParameterizedSql(rule) {
4965
+ if (!rule) {
4966
+ rule = this.getValidRules();
4967
+ }
4968
+ const obj = { sql: null };
4969
+ this.notify('query-library', { prop: 'getParameterSql', onPropertyChange: false, value: { rule: rule, obj: obj } });
4970
+ return obj['sql'];
4971
+ }
4972
+ /**
4973
+ * Sets the rules from the parameter sql query.
4974
+ *
4975
+ * @param { ParameterizedSql} sqlQuery – Specifies the parameter SQL to be passed to set the rule and load it to the query builder.
4976
+ * @returns {void}
4977
+ */
4978
+ setParameterizedSql(sqlQuery) {
4979
+ const obj = { sql: null };
4980
+ this.notify('query-library', { prop: 'convertParamSqlToSql', onPropertyChange: false, value: { sql: sqlQuery, obj: obj } });
4981
+ let sql = obj['sql'];
4982
+ if (sql) {
4983
+ sql = sql.replace(/`/g, '');
4984
+ const ruleModel = this.getRulesFromSql(sql);
4985
+ this.setRules({ condition: ruleModel.condition, not: ruleModel.not, rules: ruleModel.rules });
4986
+ }
4987
+ }
4988
+ /**
4989
+ * Gets the named parameter SQL query from rules.
4990
+ *
4991
+ * @param {RuleModel} rule – Specify the rule to be passed to get the named parameter SQL string.
4992
+ * @returns {ParameterizedNamedSql} – Parameterized Named SQL query from rules.
4993
+ */
4994
+ getParameterizedNamedSql(rule) {
4995
+ if (!rule) {
4996
+ rule = this.getValidRules();
4997
+ }
4998
+ const obj = { sql: null };
4999
+ this.notify('query-library', { prop: 'getNamedParameterSql', onPropertyChange: false, value: { rule: rule, obj: obj } });
5000
+ return obj['sql'];
5001
+ }
5002
+ /**
5003
+ * Sets the rules from the named parameter SQL query.
5004
+ *
5005
+ * @param { ParameterizedNamedSql } sqlQuery – Specifies the named parameter SQL to be passed to set the rule and load it to the query builder.
5006
+ * @returns {void}
5007
+ */
5008
+ setParameterizedNamedSql(sqlQuery) {
5009
+ const obj = { sql: null };
5010
+ this.notify('query-library', { prop: 'convertNamedParamSqlToSql', onPropertyChange: false, value: { sql: sqlQuery, obj: obj } });
5011
+ let sql = obj['sql'];
5012
+ if (sql) {
5013
+ sql = sql.replace(/`/g, '');
5014
+ const ruleModel = this.getRulesFromSql(sql);
5015
+ this.setRules({ condition: ruleModel.condition, not: ruleModel.not, rules: ruleModel.rules });
5016
+ }
5017
+ }
5018
+ /**
5019
+ * Set the rules from Mongo query.
5020
+ *
5021
+ * @param {string} mongoQuery - 'sql String' to be passed to get the rule.
5022
+ * @param {boolean} mongoLocale - Set `true` if Localization for Mongo query.
5023
+ * @returns {void}
5024
+ */
5025
+ setMongoQuery(mongoQuery, mongoLocale) {
5026
+ this.rule = { condition: 'and', not: false, rules: [] };
5027
+ this.notify('query-library', { prop: 'mongoParser', onPropertyChange: false, value: { mongoQuery: JSON.parse(mongoQuery), rule: this.rule, mongoLocale: mongoLocale } });
5028
+ }
5029
+ /**
5030
+ * Gets the Mongo query from rules.
5031
+ *
5032
+ * @param {RuleModel} rule - 'rule' to be passed to get the sql.
5033
+ * @returns {object} - Sql query from rules.
5034
+ */
5035
+ getMongoQuery(rule) {
5036
+ if (!rule) {
5037
+ rule = this.getValidRules();
5038
+ }
5039
+ const obj = { mongoQuery: null };
5040
+ this.notify('query-library', { prop: 'getMongoFromRules', onPropertyChange: false, value: { rule: rule, mongoQuery: '', obj: obj } });
5041
+ return obj['mongoQuery'];
5042
+ }
5043
+ /**
5044
+ * Clones the rule based on the rule ID to the specific group.
5045
+ *
5046
+ * @param {string} ruleID - Specifies the ruleID that needs to be cloned.
5047
+ * @param {string} groupID - Specifies the groupID in which the rule to be cloned.
5048
+ * @param {number} index - Specifies the index to insert the cloned rule inside the group.
5049
+ * @returns {void}
5050
+ */
5051
+ cloneRule(ruleID, groupID, index) {
5052
+ const getRule = this.getRule(ruleID.replace(this.element.id + '_', ''));
5053
+ groupID = groupID.replace(this.element.id + '_', '');
5054
+ this.ruleIndex = index;
5055
+ this.cloneRuleBtnClick = true;
5056
+ this.showButtons.cloneRule = true;
5057
+ this.addRules([{
5058
+ 'label': getRule.label, 'field': getRule.field, 'type': getRule.type, 'operator': getRule.operator,
5059
+ 'value': getRule.value
5060
+ }], groupID);
5061
+ this.ruleIndex = -1;
5062
+ this.cloneRuleBtnClick = false;
5063
+ this.showButtons.cloneRule = false;
5064
+ }
5065
+ /**
5066
+ * Clones the group based on the group ID to the specific group.
5067
+ *
5068
+ * @param {string} groupID - Specifies the groupID that needs to be cloned.
5069
+ * @param {string} parentGroupID - Specifies the parentGroupID in which the group to be cloned.
5070
+ * @param {number} index - Specifies the index to insert the cloned group inside the parent group.
5071
+ * @returns {void}
5072
+ */
5073
+ cloneGroup(groupID, parentGroupID, index) {
5074
+ parentGroupID = parentGroupID.replace(this.element.id + '_', '');
5075
+ const group = this.getGroup(parentGroupID);
5076
+ groupID = groupID.replace(this.element.id + '_', '');
5077
+ this.groupIndex = index;
5078
+ this.cloneGrpBtnClick = true;
5079
+ this.showButtons.cloneGroup = true;
5080
+ this.addGroups([{ 'condition': group.condition, 'not': group.not, 'rules': group.rules }], groupID);
5081
+ this.groupIndex = -1;
5082
+ this.cloneGrpBtnClick = false;
5083
+ this.showButtons.cloneGroup = false;
5084
+ }
5085
+ /**
5086
+ * Locks the rule based on the rule ID.
5087
+ *
5088
+ * @param {string} ruleID - Specifies the ruleID that needs to be locked.
5089
+ * @returns {void}
5090
+ */
5091
+ lockRule(ruleID) {
5092
+ const target = document.getElementById(ruleID).querySelectorAll('.e-lock-rule-btn')[0];
5093
+ this.ruleLock(target);
5094
+ }
5095
+ /**
5096
+ * Locks the group based on the group ID
5097
+ *
5098
+ * @param {string} groupID - Specifies the groupID that needs to be locked.
5099
+ * @returns {void}
5100
+ */
5101
+ lockGroup(groupID) {
5102
+ const target = document.getElementById(groupID).querySelectorAll('.e-lock-grp-btn')[0];
5103
+ this.groupLock(target);
4644
5104
  }
4645
5105
  sqlParser(sqlString, sqlLocale) {
4646
5106
  let st = 0;
@@ -4842,13 +5302,13 @@ let QueryBuilder = class QueryBuilder extends Component {
4842
5302
  for (let i = 0; i < localeOperator.length; i++) {
4843
5303
  if (this.sqlOperators[localeOperator[i]] === operator.toUpperCase()) {
4844
5304
  if (value && value.indexOf('%') === 0 && value[value.length - 1] === '%') {
4845
- return (localeOperator[i] === 'notcontains') ? 'notcontains' : 'contains';
5305
+ return (operator.toUpperCase() === 'NOT LIKE') ? 'notcontains' : 'contains';
4846
5306
  }
4847
5307
  else if (value && value.indexOf('%') !== 0 && value.indexOf('%') === value.length - 1) {
4848
- return (localeOperator[i] === 'notstartswith') ? 'notstartswith' : 'startswith';
5308
+ return (operator.toUpperCase() === 'NOT LIKE') ? 'notstartswith' : 'startswith';
4849
5309
  }
4850
5310
  else if (value && value.indexOf('%') === 0 && value.indexOf('%') !== value.length - 1) {
4851
- return (localeOperator[i] === 'notendswith') ? 'notendswith' : 'endswith';
5311
+ return (operator.toUpperCase() === 'NOT LIKE') ? 'notendswith' : 'endswith';
4852
5312
  }
4853
5313
  return localeOperator[i];
4854
5314
  }
@@ -5033,6 +5493,14 @@ let QueryBuilder = class QueryBuilder extends Component {
5033
5493
  }
5034
5494
  else if (parser[i + 1][0] === 'Operators') {
5035
5495
  rule.operator = this.getOperator(parser[i + 2][1], parser[i + 1][1], sqlLocale);
5496
+ if (rule.operator == "equal" && parser[i + 2][0] === "String" && parser[i + 2][1] === "''") {
5497
+ rule.operator = "isempty";
5498
+
5499
+ }
5500
+ else if (rule.operator == "notequal" && parser[i + 2][0] === "String" && parser[i + 2][1] === "''") {
5501
+ rule.operator = "isnotempty";
5502
+
5503
+ }
5036
5504
  if (parser[i + 2][0] === 'Number') {
5037
5505
  rule.type = 'number';
5038
5506
  rule.value = Number(parser[i + 2][1]);
@@ -5089,33 +5557,328 @@ let QueryBuilder = class QueryBuilder extends Component {
5089
5557
  }
5090
5558
  return rules;
5091
5559
  }
5092
- };
5093
- __decorate([
5094
- Event()
5095
- ], QueryBuilder.prototype, "created", void 0);
5096
- __decorate([
5097
- Event()
5098
- ], QueryBuilder.prototype, "actionBegin", void 0);
5099
- __decorate([
5100
- Event()
5101
- ], QueryBuilder.prototype, "beforeChange", void 0);
5102
- __decorate([
5103
- Event()
5104
- ], QueryBuilder.prototype, "change", void 0);
5105
- __decorate([
5106
- Event()
5107
- ], QueryBuilder.prototype, "dataBound", void 0);
5108
- __decorate([
5109
- Event()
5110
- ], QueryBuilder.prototype, "ruleChange", void 0);
5111
- __decorate([
5112
- Property({ ruleDelete: true, groupInsert: true, groupDelete: true })
5113
- ], QueryBuilder.prototype, "showButtons", void 0);
5114
- __decorate([
5115
- Property(false)
5116
- ], QueryBuilder.prototype, "summaryView", void 0);
5117
- __decorate([
5118
- Property(false)
5560
+ /**
5561
+ * Clone the Group
5562
+ *
5563
+ * @param {Element | string} target - 'target' to be passed to clone the group.
5564
+ * @returns {void}
5565
+ */
5566
+ groupClone(target) {
5567
+ const groupElem = target.closest('.e-rule-list').closest('.e-group-container');
5568
+ let targetGrpId;
5569
+ let groupId;
5570
+ if (typeof target === 'string') {
5571
+ groupId = this.element.id + '_' + target;
5572
+ target = document.getElementById(groupId);
5573
+ }
5574
+ else {
5575
+ targetGrpId = target.id.replace(this.element.id + '_', '');
5576
+ groupId = groupElem.id.replace(this.element.id + '_', '');
5577
+ }
5578
+ const group = this.getGroup(targetGrpId);
5579
+ this.groupIndex = Array.prototype.indexOf.call(target.closest('.e-rule-list').children, target.closest('.e-group-container'));
5580
+ this.addGroups([{ 'condition': group.condition, 'not': group.not, 'rules': group.rules }], groupId);
5581
+ this.groupIndex = -1;
5582
+ }
5583
+ ruleClone(target) {
5584
+ const ruleElem = closest(target, '.e-rule-container');
5585
+ const groupElem = target.closest('.e-rule-list').closest('.e-group-container');
5586
+ const getRule = this.getRule(target);
5587
+ const groupId = groupElem.id.replace(this.element.id + '_', '');
5588
+ const ruleElemColl = groupElem.querySelectorAll('.e-rule-container');
5589
+ for (let i = 0, iLen = ruleElemColl.length; i < iLen; i++) {
5590
+ if (ruleElem.id === ruleElemColl[i].id) {
5591
+ this.ruleIndex = i;
5592
+ }
5593
+ }
5594
+ this.addRules([{ 'label': getRule.label, 'field': getRule.field, 'type': getRule.type, 'operator': getRule.operator,
5595
+ 'value': getRule.value }], groupId);
5596
+ this.ruleIndex = -1;
5597
+ }
5598
+ ruleLock(target) {
5599
+ const ruleElem = closest(target, '.e-rule-container');
5600
+ const rule = this.getRule(ruleElem.id.replace(this.element.id + '_', ''));
5601
+ if (ruleElem.classList.contains('e-disable')) {
5602
+ rule.isLocked = false;
5603
+ this.lockItems = this.lockItems.filter(lockItem => lockItem !== ruleElem.id);
5604
+ ruleElem.classList.remove('e-disable');
5605
+ this.disableRuleControls(target, ruleElem, false);
5606
+ target.children[0].classList.add('e-unlock');
5607
+ target.children[0].classList.remove('e-lock');
5608
+ target.setAttribute('title', this.l10n.getConstant('LockRule'));
5609
+ }
5610
+ else {
5611
+ rule.isLocked = true;
5612
+ if (this.lockItems.indexOf(ruleElem.id) < 0) {
5613
+ this.lockItems.splice(this.lockItems.length - 1, 0, ruleElem.id);
5614
+ }
5615
+ ruleElem.classList.add('e-disable');
5616
+ this.disableRuleControls(target, ruleElem, true);
5617
+ target.children[0].classList.add('e-lock');
5618
+ target.children[0].classList.remove('e-unlock');
5619
+ target.setAttribute('title', this.l10n.getConstant('UnlockRule'));
5620
+ }
5621
+ }
5622
+ groupLock(target) {
5623
+ const groupElem = closest(target, '.e-group-container');
5624
+ let group = this.getGroup(groupElem.id.replace(this.element.id + '_', ''));
5625
+ const isRoot = groupElem.id.indexOf('group0') > -1;
5626
+ if (groupElem.classList.contains('e-disable')) {
5627
+ if (isRoot) {
5628
+ const newGroup = {};
5629
+ newGroup.condition = group.condition;
5630
+ newGroup.not = group.not;
5631
+ newGroup.isLocked = false;
5632
+ this.setProperties({ rule: newGroup }, true);
5633
+ }
5634
+ else {
5635
+ group.isLocked = false;
5636
+ }
5637
+ this.lockItems = this.lockItems.filter(lockItem => lockItem !== groupElem.id);
5638
+ groupElem.classList.remove('e-disable');
5639
+ this.disableHeaderControls(target, groupElem, false);
5640
+ target.children[0].classList.add('e-unlock');
5641
+ target.children[0].classList.remove('e-lock');
5642
+ target.setAttribute('title', this.l10n.getConstant('LockGroup'));
5643
+ this.updateLockItems();
5644
+ }
5645
+ else {
5646
+ if (isRoot) {
5647
+ const newGroup = {};
5648
+ newGroup.condition = group.condition;
5649
+ newGroup.not = group.not;
5650
+ newGroup.isLocked = true;
5651
+ this.setProperties({ rule: newGroup }, true);
5652
+ }
5653
+ else {
5654
+ group.isLocked = true;
5655
+ }
5656
+ if (this.lockItems.indexOf(groupElem.id) < 0) {
5657
+ this.lockItems.splice(this.lockItems.length - 1, 0, groupElem.id);
5658
+ }
5659
+ groupElem.classList.add('e-disable');
5660
+ this.disableHeaderControls(target, groupElem, true);
5661
+ target.children[0].classList.add('e-lock');
5662
+ target.children[0].classList.remove('e-unlock');
5663
+ target.setAttribute('title', this.l10n.getConstant('UnlockGroup'));
5664
+ }
5665
+ }
5666
+ updateLockItems() {
5667
+ for (let i = 0; i < this.lockItems.length; i++) {
5668
+ const idColl = this.lockItems[i].split('_');
5669
+ if (idColl.length > 2) {
5670
+ let ruleElem = this.element.querySelector('#' + this.lockItems[i]);
5671
+ const target = ruleElem.querySelector('.e-lock-rule-btn');
5672
+ ruleElem = closest(target, '.e-rule-container');
5673
+ if (!ruleElem.classList.contains('e-disable')) {
5674
+ this.ruleLock(target);
5675
+ }
5676
+ }
5677
+ else {
5678
+ let groupElem = this.element.querySelector('#' + this.lockItems[i]);
5679
+ const target = groupElem.querySelector('.e-lock-grp-btn');
5680
+ groupElem = closest(target, '.e-group-container');
5681
+ if (!groupElem.classList.contains('e-disable')) {
5682
+ this.groupLock(target);
5683
+ }
5684
+ }
5685
+ }
5686
+ }
5687
+ disableHeaderControls(target, groupElem, isDisabled) {
5688
+ const andElem = groupElem.querySelectorAll('.e-btngroup-and');
5689
+ const orElem = groupElem.querySelectorAll('.e-btngroup-or');
5690
+ const notElem = groupElem.querySelectorAll('.e-qb-toggle');
5691
+ const addElem = groupElem.querySelectorAll('.e-add-btn');
5692
+ const deleteGrpElem = groupElem.querySelectorAll('.e-deletegroup');
5693
+ const lockElem = groupElem.querySelectorAll('.e-lock-grp-btn');
5694
+ const cloneElem = groupElem.querySelectorAll('.e-clone-grp-btn');
5695
+ const groupContElem = groupElem.querySelectorAll('.e-group-container');
5696
+ for (let i = 0; i < andElem.length; i++) {
5697
+ if (isDisabled) {
5698
+ if (groupContElem[i] && groupContElem[i].classList.contains('e-disable')) {
5699
+ groupContElem[i].classList.add('e-disable');
5700
+ }
5701
+ andElem[i].disabled = true;
5702
+ orElem[i].disabled = true;
5703
+ addElem[i].disabled = true;
5704
+ if (notElem[i]) {
5705
+ notElem[i].disabled = true;
5706
+ }
5707
+ if (deleteGrpElem[i]) {
5708
+ deleteGrpElem[i].disabled = true;
5709
+ }
5710
+ if (cloneElem[i]) {
5711
+ cloneElem[i].disabled = true;
5712
+ }
5713
+ andElem[i].parentElement.classList.add('e-disabled');
5714
+ if (lockElem[i] !== target) {
5715
+ lockElem[i].disabled = true;
5716
+ lockElem[i].children[0].classList.remove('e-unlock');
5717
+ lockElem[i].children[0].classList.add('e-lock');
5718
+ }
5719
+ }
5720
+ else {
5721
+ if (groupContElem[i]) {
5722
+ groupContElem[i].classList.remove('e-disable');
5723
+ }
5724
+ andElem[i].disabled = false;
5725
+ orElem[i].disabled = false;
5726
+ addElem[i].disabled = false;
5727
+ lockElem[i].disabled = false;
5728
+ if (notElem[i]) {
5729
+ notElem[i].disabled = false;
5730
+ }
5731
+ if (deleteGrpElem[i]) {
5732
+ deleteGrpElem[i].disabled = false;
5733
+ }
5734
+ if (cloneElem[i]) {
5735
+ cloneElem[i].disabled = false;
5736
+ }
5737
+ andElem[i].parentElement.classList.remove('e-disabled');
5738
+ lockElem[i].children[0].classList.remove('e-lock');
5739
+ lockElem[i].children[0].classList.add('e-unlock');
5740
+ }
5741
+ }
5742
+ this.disableRuleControls(target, groupElem, isDisabled);
5743
+ }
5744
+ disableRuleControls(target, groupElem, isDisabled) {
5745
+ const ddlElement = groupElem.querySelectorAll('.e-control.e-dropdownlist');
5746
+ const numericElement = groupElem.querySelectorAll('.e-control.e-numerictextbox');
5747
+ const textElement = groupElem.querySelectorAll('.e-control.e-textbox');
5748
+ const dateElement = groupElem.querySelectorAll('.e-control.e-datepicker');
5749
+ const checkboxElement = groupElem.querySelectorAll('.e-control.e-checkbox');
5750
+ const radioBtnElement = groupElem.querySelectorAll('.e-control.e-radio');
5751
+ const multiSelectElement = groupElem.querySelectorAll('.e-control.e-multiselect');
5752
+ const deleteElem = groupElem.querySelectorAll('.e-rule-delete');
5753
+ const lockElem = groupElem.querySelectorAll('.e-lock-rule');
5754
+ const cloneElem = groupElem.querySelectorAll('.e-clone-rule');
5755
+ const ruleElem = groupElem.querySelectorAll('.e-rule-container');
5756
+ for (let i = 0; i < deleteElem.length; i++) {
5757
+ if (isDisabled) {
5758
+ if (ruleElem[i] && ruleElem[i].classList.contains('e-disable')) {
5759
+ ruleElem[i].classList.add('e-disable');
5760
+ }
5761
+ deleteElem[i].disabled = true;
5762
+ if (cloneElem[i]) {
5763
+ cloneElem[i].disabled = true;
5764
+ }
5765
+ if (lockElem[i] !== target) {
5766
+ lockElem[i].disabled = true;
5767
+ lockElem[i].children[0].classList.remove('e-unlock');
5768
+ lockElem[i].children[0].classList.add('e-lock');
5769
+ }
5770
+ }
5771
+ else {
5772
+ if (ruleElem[i]) {
5773
+ ruleElem[i].classList.remove('e-disable');
5774
+ }
5775
+ if (cloneElem[i]) {
5776
+ cloneElem[i].disabled = false;
5777
+ }
5778
+ deleteElem[i].disabled = false;
5779
+ lockElem[i].disabled = false;
5780
+ lockElem[i].children[0].classList.remove('e-lock');
5781
+ lockElem[i].children[0].classList.add('e-unlock');
5782
+ }
5783
+ }
5784
+ let dropDownObj;
5785
+ let numericObj;
5786
+ let textObj;
5787
+ let dateObj;
5788
+ let checkBoxObj;
5789
+ let radioBtnObj;
5790
+ let multiSelectObj;
5791
+ for (let i = 0; i < ddlElement.length; i++) {
5792
+ dropDownObj = getComponent(ddlElement[i], 'dropdownlist');
5793
+ if (isDisabled) {
5794
+ dropDownObj.enabled = false;
5795
+ }
5796
+ else {
5797
+ dropDownObj.enabled = true;
5798
+ }
5799
+ }
5800
+ for (let i = 0; i < numericElement.length; i++) {
5801
+ numericObj = getComponent(numericElement[i], 'numerictextbox');
5802
+ if (isDisabled) {
5803
+ numericObj.enabled = false;
5804
+ }
5805
+ else {
5806
+ numericObj.enabled = true;
5807
+ }
5808
+ }
5809
+ for (let i = 0; i < textElement.length; i++) {
5810
+ textObj = getComponent(textElement[i], 'textbox');
5811
+ if (isDisabled) {
5812
+ textObj.enabled = false;
5813
+ }
5814
+ else {
5815
+ textObj.enabled = true;
5816
+ }
5817
+ }
5818
+ for (let i = 0; i < dateElement.length; i++) {
5819
+ dateObj = getComponent(dateElement[i], 'datepicker');
5820
+ if (isDisabled) {
5821
+ dateObj.enabled = false;
5822
+ }
5823
+ else {
5824
+ dateObj.enabled = true;
5825
+ }
5826
+ }
5827
+ for (let i = 0; i < checkboxElement.length; i++) {
5828
+ checkBoxObj = getComponent(checkboxElement[i], 'checkbox');
5829
+ if (isDisabled) {
5830
+ checkBoxObj.disabled = true;
5831
+ }
5832
+ else {
5833
+ checkBoxObj.disabled = false;
5834
+ }
5835
+ }
5836
+ for (let i = 0; i < radioBtnElement.length; i++) {
5837
+ radioBtnObj = getComponent(radioBtnElement[i], 'radio');
5838
+ if (isDisabled) {
5839
+ radioBtnObj.disabled = true;
5840
+ }
5841
+ else {
5842
+ radioBtnObj.disabled = false;
5843
+ }
5844
+ }
5845
+ for (let i = 0; i < multiSelectElement.length; i++) {
5846
+ multiSelectObj = getComponent(multiSelectElement[i], 'multiselect');
5847
+ if (isDisabled) {
5848
+ multiSelectObj.enabled = false;
5849
+ }
5850
+ else {
5851
+ multiSelectObj.enabled = true;
5852
+ }
5853
+ }
5854
+ }
5855
+ };
5856
+ __decorate([
5857
+ Event()
5858
+ ], QueryBuilder.prototype, "created", void 0);
5859
+ __decorate([
5860
+ Event()
5861
+ ], QueryBuilder.prototype, "actionBegin", void 0);
5862
+ __decorate([
5863
+ Event()
5864
+ ], QueryBuilder.prototype, "beforeChange", void 0);
5865
+ __decorate([
5866
+ Event()
5867
+ ], QueryBuilder.prototype, "change", void 0);
5868
+ __decorate([
5869
+ Event()
5870
+ ], QueryBuilder.prototype, "dataBound", void 0);
5871
+ __decorate([
5872
+ Event()
5873
+ ], QueryBuilder.prototype, "ruleChange", void 0);
5874
+ __decorate([
5875
+ Complex({}, ShowButtons)
5876
+ ], QueryBuilder.prototype, "showButtons", void 0);
5877
+ __decorate([
5878
+ Property(false)
5879
+ ], QueryBuilder.prototype, "summaryView", void 0);
5880
+ __decorate([
5881
+ Property(false)
5119
5882
  ], QueryBuilder.prototype, "allowValidation", void 0);
5120
5883
  __decorate([
5121
5884
  Property('Default')
@@ -5171,6 +5934,15 @@ __decorate([
5171
5934
  __decorate([
5172
5935
  Property(false)
5173
5936
  ], QueryBuilder.prototype, "readonly", void 0);
5937
+ __decorate([
5938
+ Property(true)
5939
+ ], QueryBuilder.prototype, "addRuleToNewGroups", void 0);
5940
+ __decorate([
5941
+ Property(false)
5942
+ ], QueryBuilder.prototype, "autoSelectField", void 0);
5943
+ __decorate([
5944
+ Property(true)
5945
+ ], QueryBuilder.prototype, "autoSelectOperator", void 0);
5174
5946
  __decorate([
5175
5947
  Property('')
5176
5948
  ], QueryBuilder.prototype, "separator", void 0);
@@ -5181,6 +5953,692 @@ QueryBuilder = __decorate([
5181
5953
  NotifyPropertyChanges
5182
5954
  ], QueryBuilder);
5183
5955
 
5956
+ class QueryLibrary {
5957
+ constructor(parent) {
5958
+ this.parent = parent;
5959
+ this.addEventListener();
5960
+ }
5961
+ destroy() {
5962
+ if (this.parent.isDestroyed) {
5963
+ return;
5964
+ }
5965
+ this.removeEventListener();
5966
+ }
5967
+ addEventListener() {
5968
+ if (this.parent.isDestroyed) {
5969
+ return;
5970
+ }
5971
+ this.parent.on('query-library', this.queryLibrary, this);
5972
+ this.parent.on('destroyed', this.destroy, this);
5973
+ }
5974
+ removeEventListener() {
5975
+ this.parent.off('query-library', this.queryLibrary);
5976
+ this.parent.off('destroyed', this.destroy);
5977
+ }
5978
+ queryLibrary(args) {
5979
+ switch (args.prop) {
5980
+ case 'getMongoFromRules':
5981
+ args.value['obj']['mongoQuery'] = this.getMongoFromRules(args.value['rule'], args.value['mongoQuery']);
5982
+ break;
5983
+ case 'mongoParser':
5984
+ this.mongoParser(args.value['mongoQuery'], args.value['rule'], args.value['mongoLocale']);
5985
+ break;
5986
+ case 'getParameterSql':
5987
+ args.value['obj']['sql'] = this.getParameterSql(args.value['rule']);
5988
+ break;
5989
+ case 'getNamedParameterSql':
5990
+ args.value['obj']['sql'] = this.getNamedParameterSql(args.value['rule']);
5991
+ break;
5992
+ case 'convertParamSqlToSql':
5993
+ args.value['obj']['sql'] = this.convertParamSqlToSql(args.value['sql']);
5994
+ break;
5995
+ case 'convertNamedParamSqlToSql':
5996
+ args.value['obj']['sql'] = this.convertNamedParamSqlToSql(args.value['sql']);
5997
+ break;
5998
+ }
5999
+ }
6000
+ getMongoFromRules(rule, mongoQuery) {
6001
+ mongoQuery = '{';
6002
+ if (rule.condition === 'or') {
6003
+ mongoQuery += '"$or":[';
6004
+ mongoQuery = this.convertMongoQuery(rule.rules, mongoQuery) + ']';
6005
+ }
6006
+ else {
6007
+ mongoQuery += '"$and":[';
6008
+ mongoQuery = this.convertMongoQuery(rule.rules, mongoQuery) + ']';
6009
+ }
6010
+ mongoQuery += '}';
6011
+ return mongoQuery;
6012
+ }
6013
+ getOperatorFromMongoOperator(operator) {
6014
+ let operatorValue;
6015
+ switch (operator) {
6016
+ case '$ne':
6017
+ operatorValue = 'notequal';
6018
+ break;
6019
+ case '$gt':
6020
+ operatorValue = 'greaterthan';
6021
+ break;
6022
+ case '$gte':
6023
+ operatorValue = 'greaterthanorequal';
6024
+ break;
6025
+ case '$lt':
6026
+ operatorValue = 'lessthan';
6027
+ break;
6028
+ case '$lte':
6029
+ operatorValue = 'lessthanorequal';
6030
+ break;
6031
+ case '$nin':
6032
+ operatorValue = 'notin';
6033
+ break;
6034
+ }
6035
+ return operatorValue;
6036
+ }
6037
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6038
+ convertMongoQuery(rules, mongoQuery) {
6039
+ let i = 0;
6040
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6041
+ rules.forEach((item) => {
6042
+ i++;
6043
+ mongoQuery += '{';
6044
+ if (item.rules !== undefined) {
6045
+ if (item.condition === 'or') {
6046
+ mongoQuery += ' "$or":[';
6047
+ mongoQuery = this.convertMongoQuery(item.rules, mongoQuery) + ']';
6048
+ }
6049
+ else {
6050
+ mongoQuery += ' "$and":[';
6051
+ mongoQuery = this.convertMongoQuery(item.rules, mongoQuery) + ']';
6052
+ }
6053
+ }
6054
+ let itVal = item.type === 'string' && item.operator !== 'in' && item.operator !== 'notin' && item.value && item.value.trim() !== '' ? item.value.replace(/'/g, '\\') : '';
6055
+ if (item.type === 'string' && (item.operator === 'in' || item.operator === 'notin') && item.value && item.value.length === 1) {
6056
+ itVal = item.value[0].replace(/'/g, '\\');
6057
+ }
6058
+ const field = item.field ? item.field.substring(0) : '';
6059
+ switch (item.operator) {
6060
+ case 'contains':
6061
+ mongoQuery += '"' + field + '":{"$regex":"' + itVal + '"}';
6062
+ break;
6063
+ case 'notcontains':
6064
+ mongoQuery += '"' + field + '":{"$not":{"$regex":"' + item.value + '"}}';
6065
+ break;
6066
+ case 'startswith':
6067
+ mongoQuery += '"' + field + '":{"$regex":"^' + itVal + '"}';
6068
+ break;
6069
+ case 'notstartswith':
6070
+ mongoQuery += '"' + field + '":{"$not":{"$regex":"^' + item.value + '"}}';
6071
+ break;
6072
+ case 'endswith':
6073
+ mongoQuery += '"' + field + '":{"$regex":"' + itVal + '$"}';
6074
+ break;
6075
+ case 'notendswith':
6076
+ mongoQuery += '"' + field + '":{"$not":{"$regex":"' + item.value + '$"}}';
6077
+ break;
6078
+ case 'isnull':
6079
+ mongoQuery += '"' + field + '": null';
6080
+ break;
6081
+ case 'isnotnull':
6082
+ mongoQuery += '"' + field + '":{"$ne": null}';
6083
+ break;
6084
+ case 'isempty':
6085
+ mongoQuery += '"' + field + '": ""';
6086
+ break;
6087
+ case 'isnotempty':
6088
+ mongoQuery += '"' + field + '":{"$ne": ""}';
6089
+ break;
6090
+ case 'equal':
6091
+ if (item.type === 'string') {
6092
+ mongoQuery += '"' + field + '":"' + itVal + '"';
6093
+ }
6094
+ else if (item.type === 'date') {
6095
+ mongoQuery += '"' + field + '":"' + item.value + '"';
6096
+ }
6097
+ else if (item.type === 'boolean') {
6098
+ mongoQuery += '"' + field + '":' + item.value + '';
6099
+ }
6100
+ else {
6101
+ mongoQuery += '"' + field + '":' + item.value + '';
6102
+ }
6103
+ break;
6104
+ case 'notequal':
6105
+ if (item.type === 'string') {
6106
+ mongoQuery += '"' + field + '":{"$ne":"' + itVal + '"}';
6107
+ }
6108
+ else if (item.type === 'date') {
6109
+ mongoQuery += '"' + field + '":{"$ne":"' + item.value + '"}';
6110
+ }
6111
+ else {
6112
+ mongoQuery += '"' + field + '":{"$ne":' + item.value + '}';
6113
+ }
6114
+ break;
6115
+ case 'in':
6116
+ if (item.type === 'string') {
6117
+ if (item.value.length > 1) {
6118
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6119
+ let s = item.value.map((x, j) => (j < item.value.length ? `"${x}"` : '')).toString();
6120
+ s = s.endsWith(',') ? s.substring(0, s.length - 1) : s;
6121
+ mongoQuery += '"' + field + '": { "$in": [' + s + ']}';
6122
+ }
6123
+ else {
6124
+ mongoQuery += '"' + field + '": { "$in": ["' + itVal + '"]}';
6125
+ }
6126
+ }
6127
+ else if (item.type === 'number') {
6128
+ if (item.value.length > 1) {
6129
+ mongoQuery += '"' + field + '": { "$in": [' + item.value.toString() + ']}';
6130
+ }
6131
+ else {
6132
+ mongoQuery += '"' + field + '": { "$in": [' + item.value + ']}';
6133
+ }
6134
+ }
6135
+ break;
6136
+ case 'notin':
6137
+ if (item.type === 'string') {
6138
+ if (item.value.length > 1) {
6139
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6140
+ let s = item.value.map((x, j) => (j < item.value.length ? `"${x}"` : '')).toString();
6141
+ s = s.endsWith(',') ? s.substring(0, s.length - 1) : s;
6142
+ mongoQuery += '"' + field + '": { "$nin": [' + s + ']}';
6143
+ }
6144
+ else {
6145
+ mongoQuery += '"' + field + '": { "$nin": ["' + itVal + '"]}';
6146
+ }
6147
+ }
6148
+ else if (item.type === 'number') {
6149
+ if (item.value.length > 1) {
6150
+ mongoQuery += '"' + field + '": { "$nin": [' + item.value.toString() + ']}';
6151
+ }
6152
+ else {
6153
+ mongoQuery += '"' + field + '": { "$nin": [' + item.value + ']}';
6154
+ }
6155
+ }
6156
+ break;
6157
+ case 'greaterthan':
6158
+ if (item.type === 'number') {
6159
+ mongoQuery += '"' + field + '": { "$gt": ' + item.value + '}';
6160
+ }
6161
+ else {
6162
+ mongoQuery += '"' + field + '": { "$gt": "' + item.value + '"}';
6163
+ }
6164
+ break;
6165
+ case 'greaterthanorequal':
6166
+ if (item.type === 'number') {
6167
+ mongoQuery += '"' + field + '": { "$gte": ' + item.value + '}';
6168
+ }
6169
+ else {
6170
+ mongoQuery += '"' + field + '": { "$gte": "' + item.value + '"}';
6171
+ }
6172
+ break;
6173
+ case 'between':
6174
+ if (item.type === 'number') {
6175
+ mongoQuery += '"' + field + '": {"$gte":' + item.value[0] + ', "$lte":' + item.value[1] + '}';
6176
+ }
6177
+ else {
6178
+ mongoQuery += '"' + field + '": {"$gte": "' + item.value[0] + '", "$lte": "' + item.value[1] + '"}';
6179
+ }
6180
+ break;
6181
+ case 'notbetween':
6182
+ if (item.type === 'number') {
6183
+ mongoQuery += '"$or":[{"' + field + '": {"$lt":' + item.value[0] + '}}, {"' + field + '": {"$gt":' + item.value[1] + '}}]';
6184
+ }
6185
+ else {
6186
+ mongoQuery += '"$or":[{"' + field + '": {"$lt": "' + item.value[0] + '"}}, {"' + field + '": {"$gt": "' + item.value[1] + '"}}]';
6187
+ }
6188
+ break;
6189
+ case 'lessthan':
6190
+ if (item.type === 'number') {
6191
+ mongoQuery += '"' + field + '": { "$lt": ' + item.value + '}';
6192
+ }
6193
+ else {
6194
+ mongoQuery += '"' + field + '": { "$lt": "' + item.value + '"}';
6195
+ }
6196
+ break;
6197
+ case 'lessthanorequal':
6198
+ if (item.type === 'number') {
6199
+ mongoQuery += '"' + field + '": { "$lte": ' + item.value + '}';
6200
+ }
6201
+ else {
6202
+ mongoQuery += '"' + field + '": { "$lte": "' + item.value + '"}';
6203
+ }
6204
+ break;
6205
+ }
6206
+ mongoQuery += '}';
6207
+ if (rules.length !== i) {
6208
+ mongoQuery += ',';
6209
+ }
6210
+ });
6211
+ return mongoQuery;
6212
+ }
6213
+ mongoParser(mongoQuery, rule, mongoLocale) {
6214
+ let mongoList;
6215
+ if (Object.keys(mongoQuery).indexOf('$and') > -1) {
6216
+ mongoList = mongoQuery['$and'];
6217
+ rule.condition = 'and';
6218
+ }
6219
+ else if (Object.keys(mongoQuery).indexOf('$or') > -1) {
6220
+ mongoList = mongoQuery['$or'];
6221
+ rule.condition = 'or';
6222
+ }
6223
+ rule.rules = [];
6224
+ this.mongoRecursion(mongoList, rule.rules, mongoLocale);
6225
+ }
6226
+ mongoRecursion(mongoList, rules, mongoLocale) {
6227
+ let operatorValue;
6228
+ let type;
6229
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6230
+ let stringValue;
6231
+ let key;
6232
+ let betweenValue;
6233
+ let condition;
6234
+ let value;
6235
+ let subRules;
6236
+ let rule;
6237
+ let keyObj;
6238
+ let ruleValue;
6239
+ for (let i = 0, len = mongoList.length; i < len; i++) {
6240
+ const betweenOperatorArray = [];
6241
+ let inOperatorArray = [];
6242
+ condition = Object.keys(mongoList[i])[0];
6243
+ value = mongoList[i][condition];
6244
+ if (condition === '$and') {
6245
+ if (this.parent.enableNotCondition) {
6246
+ subRules = { condition: condition.replace('$', ''), rules: [], not: false };
6247
+ }
6248
+ else {
6249
+ subRules = { condition: condition.replace('$', ''), rules: [] };
6250
+ }
6251
+ rules.push(subRules);
6252
+ this.mongoRecursion(mongoList[i][condition], rules[rules.length - 1].rules, mongoLocale);
6253
+ }
6254
+ else if (condition === '$or') {
6255
+ let notBetween;
6256
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any, max-len
6257
+ let innerObject = [];
6258
+ let keys = [];
6259
+ let firstKey = [];
6260
+ let secondKey = [];
6261
+ let innerKeys = [];
6262
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any, max-len
6263
+ let firstValue = [];
6264
+ let secondValue = [];
6265
+ let innerFirstValue = [];
6266
+ let innerSecondValue = [];
6267
+ if (Array.isArray(value) && value.length === 2) {
6268
+ keys = Object.keys(value);
6269
+ innerFirstValue = value[keys[0]];
6270
+ innerSecondValue = value[keys[1]];
6271
+ if (typeof innerFirstValue === 'object') {
6272
+ innerObject = Object.keys(innerFirstValue)[0];
6273
+ innerKeys = Object.keys(innerFirstValue[Object.keys(innerFirstValue)[0]]);
6274
+ firstKey = innerKeys[0];
6275
+ secondKey = Object.keys(innerSecondValue[Object.keys(innerSecondValue)[0]])[0];
6276
+ if (firstKey === '$lt' && secondKey === '$gt') {
6277
+ operatorValue = 'notbetween';
6278
+ // eslint-disable-next-line security/detect-object-injection
6279
+ firstValue = innerFirstValue[innerObject][firstKey];
6280
+ // eslint-disable-next-line security/detect-object-injection
6281
+ secondValue = innerSecondValue[innerObject][secondKey];
6282
+ type = typeof firstValue === 'number' ? 'number' : 'date';
6283
+ ruleValue = [firstValue, secondValue];
6284
+ rule = { field: innerObject, label: innerObject, value: ruleValue, operator: operatorValue, type: type };
6285
+ rules.push(rule);
6286
+ notBetween = true;
6287
+ }
6288
+ }
6289
+ }
6290
+ if (!notBetween) {
6291
+ if (this.parent.enableNotCondition) {
6292
+ subRules = { condition: condition.replace('$', ''), rules: [], not: false };
6293
+ }
6294
+ else {
6295
+ subRules = { condition: condition.replace('$', ''), rules: [] };
6296
+ }
6297
+ rules.push(subRules);
6298
+ this.mongoRecursion(mongoList[i][condition], rules[rules.length - 1].rules, mongoLocale);
6299
+ }
6300
+ }
6301
+ else {
6302
+ value = mongoList[i][condition];
6303
+ if (value === null) { // isnull operator
6304
+ operatorValue = 'isnull';
6305
+ }
6306
+ if (typeof value === 'boolean') { // boolean type values
6307
+ operatorValue = 'equal';
6308
+ type = 'boolean';
6309
+ ruleValue = value;
6310
+ }
6311
+ if (typeof (value) === 'number') {
6312
+ ruleValue = value;
6313
+ type = 'number';
6314
+ operatorValue = 'equal';
6315
+ }
6316
+ else if (typeof (value) === 'object' && value !== null) {
6317
+ keyObj = Object.keys(value);
6318
+ for (let i = 0; i < keyObj.length; i++) {
6319
+ key = keyObj[i];
6320
+ stringValue = (value)[keyObj[i]];
6321
+ if (key === '$ne' && isNullOrUndefined(stringValue)) { // not null operator
6322
+ operatorValue = 'isnotnull';
6323
+ ruleValue = null;
6324
+ }
6325
+ if (key === '$ne' && typeof stringValue === 'boolean') { // not equal operator for boolean
6326
+ operatorValue = 'notequal';
6327
+ ruleValue = stringValue;
6328
+ type = 'boolean';
6329
+ }
6330
+ if (keyObj.length >= 2 && keyObj[i]) {
6331
+ if (typeof (stringValue) == 'object') { // between and notbetween operators
6332
+ operatorValue = 'notbetween';
6333
+ condition = Object.keys(stringValue)[0];
6334
+ betweenValue = [Object.keys(stringValue[condition])[0]];
6335
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6336
+ betweenOperatorArray.push(stringValue[condition][betweenValue]);
6337
+ type = 'number';
6338
+ }
6339
+ else {
6340
+ operatorValue = 'between';
6341
+ betweenOperatorArray.push(stringValue);
6342
+ }
6343
+ if (typeof (stringValue) === 'number') {
6344
+ type = 'number';
6345
+ }
6346
+ }
6347
+ else if (typeof (stringValue) === 'object' && stringValue !== null) { // "in" and "notin" operator
6348
+ if (key === '$not' && Object.keys(stringValue)[0] === '$regex') {
6349
+ if (stringValue['$regex'].indexOf('^') > -1) {
6350
+ operatorValue = 'notstartswith';
6351
+ ruleValue = stringValue['$regex'].replace('^', '');
6352
+ }
6353
+ else if (stringValue['$regex'].indexOf('$') > -1) {
6354
+ operatorValue = 'notendswith';
6355
+ ruleValue = stringValue['$regex'].replace('$', '');
6356
+ }
6357
+ else {
6358
+ operatorValue = 'notcontains';
6359
+ ruleValue = stringValue['$regex'];
6360
+ }
6361
+ }
6362
+ else {
6363
+ operatorValue = key === '$in' ? 'in' : 'notin';
6364
+ inOperatorArray = stringValue;
6365
+ type = typeof (stringValue[0]) === 'number' ? 'number' : 'string';
6366
+ }
6367
+ }
6368
+ else if (typeof (stringValue) === 'number') { // number type values
6369
+ operatorValue = this.getOperatorFromMongoOperator(key);
6370
+ type = 'number';
6371
+ ruleValue = stringValue;
6372
+ }
6373
+ if (typeof (stringValue) === 'string') { // string type values
6374
+ if (key === '$regex') {
6375
+ operatorValue = 'contains';
6376
+ ruleValue = stringValue;
6377
+ type = 'string';
6378
+ }
6379
+ if (key === '$ne') { // not equal
6380
+ if (stringValue !== null && stringValue.length > 0 && isNaN(Date.parse(stringValue))) {
6381
+ operatorValue = 'notequal';
6382
+ ruleValue = stringValue;
6383
+ }
6384
+ else if (isNullOrUndefined(stringValue)) { // is not null operator
6385
+ operatorValue = 'isnotnull';
6386
+ ruleValue = stringValue;
6387
+ }
6388
+ else if (stringValue === '') { // is not empty operator
6389
+ operatorValue = 'isnotempty';
6390
+ ruleValue = stringValue;
6391
+ }
6392
+ type = 'string';
6393
+ }
6394
+ if (stringValue.indexOf('^') > -1) {
6395
+ operatorValue = 'startswith';
6396
+ ruleValue = stringValue.replace('^', '');
6397
+ type = 'string';
6398
+ }
6399
+ if (stringValue.indexOf('$') > -1 && key !== '$not') {
6400
+ operatorValue = 'endswith';
6401
+ ruleValue = stringValue.replace('$', '');
6402
+ type = 'string';
6403
+ }
6404
+ if (!isNaN(Date.parse(stringValue))) { // Date type operators
6405
+ operatorValue = operatorValue || this.getOperatorFromMongoOperator(key);
6406
+ type = 'date';
6407
+ ruleValue = stringValue;
6408
+ }
6409
+ }
6410
+ }
6411
+ }
6412
+ else if (value && typeof (value) === 'string' && !isNaN(Date.parse(value))) {
6413
+ operatorValue = 'equal';
6414
+ ruleValue = value;
6415
+ type = 'date';
6416
+ }
6417
+ else if (typeof (value) === 'string' && value !== '' && value !== 'true' && value !== 'false') {
6418
+ operatorValue = 'equal';
6419
+ ruleValue = value;
6420
+ type = 'string';
6421
+ }
6422
+ else if (typeof (value) === 'string' && value === '') {
6423
+ operatorValue = 'isempty';
6424
+ ruleValue = value;
6425
+ type = 'string';
6426
+ }
6427
+ if (betweenOperatorArray && betweenOperatorArray.length > 1) { // between opertor value
6428
+ rule = { field: condition, label: condition, value: betweenOperatorArray, operator: operatorValue, type: type };
6429
+ }
6430
+ else if (inOperatorArray && inOperatorArray.length > 1) { // in operator value
6431
+ rule = { field: condition, label: condition, value: inOperatorArray, operator: operatorValue, type: type };
6432
+ }
6433
+ else {
6434
+ rule = { field: condition, label: condition, value: ruleValue, operator: operatorValue, type: type };
6435
+ }
6436
+ rules.push(rule);
6437
+ operatorValue = '';
6438
+ }
6439
+ }
6440
+ }
6441
+ convertParamSqlToSql(sql) {
6442
+ const paramSql = sql.sql;
6443
+ const paramValues = sql.params;
6444
+ const parts = paramSql.split('?');
6445
+ let normalSql = parts[0];
6446
+ for (let i = 0; i < paramValues.length; i++) {
6447
+ normalSql += (typeof (paramValues[i]) === 'string' ? `'${paramValues[i]}'` + parts[i + 1] : paramValues[i] + parts[i + 1]);
6448
+ }
6449
+ if (normalSql.length >= 2 && normalSql[0] === '(' && normalSql[normalSql.length - 1] === ')') {
6450
+ normalSql = normalSql.slice(1, -1);
6451
+ }
6452
+ normalSql = normalSql.replace(/!= ''(?! =)/g, 'IS NOT EMPTY').replace(/= ''/g, 'IS EMPTY');
6453
+ return normalSql;
6454
+ }
6455
+ convertNamedParamSqlToSql(sql) {
6456
+ const namedParamSql = sql.sql;
6457
+ const params = sql.params;
6458
+ let normalSql = namedParamSql;
6459
+ Object.keys(params).forEach((paramName) => {
6460
+ const paramValue = params[paramName];
6461
+ paramName = ':' + paramName;
6462
+ normalSql = normalSql.replace(paramName, typeof (paramValue) === 'string' ? `'${paramValue}'` : String(paramValue));
6463
+ });
6464
+ if (normalSql.length >= 2 && normalSql[0] === '(' && normalSql[normalSql.length - 1] === ')') {
6465
+ normalSql = normalSql.slice(1, -1);
6466
+ }
6467
+ normalSql = normalSql.replace(/!= ''(?! =)/g, 'IS NOT EMPTY').replace(/= ''/g, 'IS EMPTY');
6468
+ return normalSql;
6469
+ }
6470
+ getParameterSql(qbrule) {
6471
+ const qbRule = extend({}, qbrule, null, true);
6472
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6473
+ const value = this.updateRuleValue(qbRule, false);
6474
+ return this.getParameterSQLVal(this.parent.getSqlFromRules(qbRule), value['ruleVal']);
6475
+ }
6476
+ getNamedParameterSql(qbrule) {
6477
+ const qbRule = extend({}, qbrule, null, true);
6478
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6479
+ const value = this.updateRuleValue(qbRule, true);
6480
+ return this.getNamedParameterSQLVal(this.parent.getSqlFromRules(qbRule), value['namedRuleVal']);
6481
+ }
6482
+ getParameterSQLVal(content, ruleValue) {
6483
+ const replacedString = content.replace(/[%']/g, '');
6484
+ return { sql: '(' + replacedString + ')', params: ruleValue };
6485
+ }
6486
+ getNamedParameterSQLVal(content, ruleValue) {
6487
+ const replacedString = content.replace(/[%']/g, '');
6488
+ return { sql: '(' + replacedString + ')', params: ruleValue };
6489
+ }
6490
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6491
+ updateRuleValue(rule, isNamedParameter) {
6492
+ const ruleVal = [];
6493
+ const namedRuleVal = {};
6494
+ const namedParameters = [];
6495
+ return this.updateValue(rule.rules, isNamedParameter, ruleVal, namedRuleVal, namedParameters);
6496
+ }
6497
+ updateValue(rules, isNamedParameter, ruleVal,
6498
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6499
+ namedRuleVal, namedParameters) {
6500
+ if (isNullOrUndefined(rules)) {
6501
+ return { ruleVal, namedRuleVal };
6502
+ }
6503
+ for (let i = 0; i < rules.length; i++) {
6504
+ if (rules[i].rules) {
6505
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6506
+ const value = this.updateValue(rules[i].rules, isNamedParameter, ruleVal, namedRuleVal, namedParameters);
6507
+ ruleVal = value['ruleVal'];
6508
+ namedRuleVal = value['namedRuleVal'];
6509
+ }
6510
+ else {
6511
+ let namedField;
6512
+ if (rules[i].value instanceof Array) {
6513
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6514
+ for (let j = 0; j < (rules[i].value).length; j++) {
6515
+ if (isNamedParameter) {
6516
+ namedField = this.getNamedParameter(rules[i].field, namedParameters);
6517
+ }
6518
+ if (!isNullOrUndefined(rules[i].value[j])) {
6519
+ if (rules[i].type === 'string' || rules[i].type === 'date') {
6520
+ if (isNamedParameter) {
6521
+ namedRuleVal[namedField] = rules[i].value[j];
6522
+ }
6523
+ else {
6524
+ ruleVal.push(rules[i].value[j]);
6525
+ }
6526
+ }
6527
+ else {
6528
+ if (isNamedParameter) {
6529
+ namedRuleVal[namedField] = rules[i].value[j];
6530
+ }
6531
+ else {
6532
+ ruleVal.push(rules[i].value[j]);
6533
+ }
6534
+ }
6535
+ }
6536
+ if (isNamedParameter) {
6537
+ rules[i].value[j] = ':' + namedField;
6538
+ }
6539
+ else {
6540
+ rules[i].value[j] = '?';
6541
+ }
6542
+ }
6543
+ }
6544
+ else {
6545
+ if (isNamedParameter) {
6546
+ namedField = this.getNamedParameter(rules[i].field, namedParameters);
6547
+ }
6548
+ if (rules[i].operator.indexOf('null') < 1) {
6549
+ if (rules[i].type !== 'string' || (rules[i].type === 'string' && (rules[i].value !== '' || rules[i].value === 0))) {
6550
+ if (rules[i].type === 'string' || rules[i].type === 'date') {
6551
+ if (rules[i].operator.indexOf('empty') < 1) {
6552
+ let value = rules[i].value.toString();
6553
+ switch (rules[i].operator) {
6554
+ case 'startswith':
6555
+ case 'notstartswith':
6556
+ value = value + '%';
6557
+ break;
6558
+ case 'endswith':
6559
+ case 'notendswith':
6560
+ value = '%' + value;
6561
+ break;
6562
+ case 'contains':
6563
+ case 'notcontains':
6564
+ value = '%' + value + '%';
6565
+ break;
6566
+ }
6567
+ if (isNamedParameter) {
6568
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6569
+ namedRuleVal[namedField] = value;
6570
+ }
6571
+ else {
6572
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6573
+ ruleVal.push(value);
6574
+ }
6575
+ }
6576
+ else {
6577
+ if (isNamedParameter) {
6578
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6579
+ namedRuleVal[namedField] = '';
6580
+ }
6581
+ else {
6582
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6583
+ ruleVal.push('');
6584
+ }
6585
+ if (rules[i].operator === 'isempty') {
6586
+ rules[i].operator = 'equal';
6587
+ }
6588
+ else {
6589
+ rules[i].operator = 'notequal';
6590
+ }
6591
+ }
6592
+ }
6593
+ else {
6594
+ if (!isNullOrUndefined(rules[i].value)) {
6595
+ if (isNamedParameter) {
6596
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6597
+ namedRuleVal[namedField] = rules[i].value;
6598
+ }
6599
+ else {
6600
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
6601
+ ruleVal.push(rules[i].value);
6602
+ }
6603
+ }
6604
+ }
6605
+ if (isNamedParameter) {
6606
+ rules[i].value = ':' + namedField;
6607
+ }
6608
+ else {
6609
+ rules[i].value = '?';
6610
+ }
6611
+ }
6612
+ }
6613
+ }
6614
+ }
6615
+ }
6616
+ return { ruleVal, namedRuleVal };
6617
+ }
6618
+ getNamedParameter(field, namedParameters) {
6619
+ let newField = null;
6620
+ if (namedParameters.length > 0) {
6621
+ for (let i = namedParameters.length - 1; i >= 0; i--) {
6622
+ const currField = namedParameters[i];
6623
+ if (currField.indexOf(field) > -1) {
6624
+ const idx = parseInt(currField.split('_')[1], 10) + 1;
6625
+ newField = field + '_' + idx;
6626
+ namedParameters.push(newField);
6627
+ break;
6628
+ }
6629
+ }
6630
+ }
6631
+ if (!newField) {
6632
+ newField = field + '_1';
6633
+ namedParameters.push(newField);
6634
+ }
6635
+ return newField;
6636
+ }
6637
+ getModuleName() {
6638
+ return 'query-library';
6639
+ }
6640
+ }
6641
+
5184
6642
  /**
5185
6643
  * QueryBuilder modules
5186
6644
  */
@@ -5189,5 +6647,5 @@ QueryBuilder = __decorate([
5189
6647
  * QueryBuilder all modules
5190
6648
  */
5191
6649
 
5192
- export { Columns, Rule, Value, ShowButtons, QueryBuilder };
6650
+ export { Columns, Rule, Value, ShowButtons, QueryBuilder, QueryLibrary };
5193
6651
  //# sourceMappingURL=ej2-querybuilder.es2015.js.map