@flowerforce/flower-core 3.3.1-beta.1 → 4.0.1-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/dist/index.cjs.js +241 -271
  2. package/dist/index.esm.js +231 -270
  3. package/dist/src/constants/index.d.ts +5 -0
  4. package/dist/src/event-emitter/index.d.ts +1 -0
  5. package/dist/src/index.d.ts +6 -8
  6. package/dist/src/interfaces/CoreInterface.d.ts +23 -17
  7. package/dist/src/interfaces/ReducerInterface.d.ts +117 -99
  8. package/dist/src/{rules-matcher/interface.d.ts → interfaces/RulesMatcherInterface.d.ts} +1 -1
  9. package/dist/src/interfaces/SelectorsInterface.d.ts +21 -12
  10. package/dist/src/interfaces/Store.d.ts +2 -10
  11. package/dist/src/interfaces/UtilsInterface.d.ts +1 -1
  12. package/dist/src/interfaces/index.d.ts +3 -0
  13. package/dist/src/rules-matcher/RulesMatcher.d.ts +2 -0
  14. package/dist/src/rules-matcher/index.d.ts +2 -0
  15. package/dist/src/rules-matcher/utils.d.ts +2 -3
  16. package/dist/src/state-manager/index.d.ts +2 -0
  17. package/dist/src/state-manager/state-functions/FlowerCoreMergedReducers.d.ts +2 -0
  18. package/dist/src/state-manager/state-functions/FlowerCoreStateFunctions.d.ts +5 -0
  19. package/dist/src/state-manager/state-functions/FlowerDataStateFunctions.d.ts +13 -0
  20. package/dist/src/state-manager/state-functions/index.d.ts +4 -0
  21. package/dist/src/state-manager/state-selectors/FlowerCoreStateSelectors.d.ts +2 -0
  22. package/dist/src/state-manager/state-selectors/FlowerFormStateSelectors.d.ts +2 -0
  23. package/dist/src/state-manager/state-selectors/FlowerSelectorsMerged.d.ts +2 -0
  24. package/dist/src/state-manager/state-selectors/index.d.ts +4 -0
  25. package/dist/src/{FlowerCoreStateUtils.d.ts → utils/FlowerCoreStateUtils.d.ts} +2 -2
  26. package/dist/src/{CoreUtils.d.ts → utils/FlowerCoreUtils.d.ts} +1 -2
  27. package/dist/src/utils/FlowerFlowUtils.d.ts +3 -0
  28. package/dist/src/utils/FlowerFormCoreUtils.d.ts +2 -0
  29. package/dist/src/utils/index.d.ts +4 -0
  30. package/package.json +1 -1
  31. package/dist/src/FlowerCoreStateFunctions.d.ts +0 -5
  32. package/dist/src/FlowerCoreStateSelectors.d.ts +0 -2
  33. package/dist/src/RulesMatcher.d.ts +0 -5
  34. package/dist/src/devtoolState.d.ts +0 -2
  35. /package/dist/src/{Emitter.d.ts → event-emitter/Emitter.d.ts} +0 -0
package/dist/index.cjs.js CHANGED
@@ -1,13 +1,7 @@
1
1
  'use strict';
2
2
 
3
3
  var tinyEmitter = require('tiny-emitter');
4
- var _set = require('lodash/set');
5
- var _unset = require('lodash/unset');
6
4
  var _get = require('lodash/get');
7
- var _last = require('lodash/last');
8
- var _slice = require('lodash/slice');
9
- var _cloneDeep = require('lodash/cloneDeep');
10
- var lastIndexOf = require('lodash/lastIndexOf');
11
5
  var find = require('lodash/find');
12
6
  var keyBy = require('lodash/keyBy');
13
7
  var has = require('lodash/has');
@@ -18,10 +12,56 @@ var mapKeys = require('lodash/mapKeys');
18
12
  var mapValues = require('lodash/mapValues');
19
13
  var _trimStart = require('lodash/trimStart');
20
14
  var _intersection = require('lodash/intersection');
15
+ var _set = require('lodash/set');
16
+ var _last = require('lodash/last');
17
+ var _slice = require('lodash/slice');
18
+ var _cloneDeep = require('lodash/cloneDeep');
19
+ var lastIndexOf = require('lodash/lastIndexOf');
20
+ var _unset = require('lodash/unset');
21
21
  var flat = require('flat');
22
22
 
23
23
  const Emitter = new tinyEmitter.TinyEmitter();
24
24
 
25
+ exports.REDUCER_NAME = void 0;
26
+ (function (REDUCER_NAME) {
27
+ REDUCER_NAME["FLOWER_FLOW"] = "FlowerFlow";
28
+ REDUCER_NAME["FLOWER_DATA"] = "FlowerData";
29
+ })(exports.REDUCER_NAME || (exports.REDUCER_NAME = {}));
30
+ const devtoolState = {};
31
+
32
+ const FlowerStateUtils = {
33
+ getAllData: (state) => state &&
34
+ Object.entries(state ?? {}).reduce((acc, [k, v]) => ({ ...acc, [k]: v?.data ?? v }), {}),
35
+ selectFlowerFormNode: (name) => (state) => _get(state, name),
36
+ makeSelectCurrentNextRules: (name) => (state) => {
37
+ const nextRules = _get(state, [name, 'nextRules']);
38
+ const currentNodeId = FlowerStateUtils.makeSelectCurrentNodeId(name)(state);
39
+ return _get(nextRules, [currentNodeId]);
40
+ },
41
+ makeSelectCurrentNodeId: (name) => (state) => {
42
+ const subState = _get(state, [name]);
43
+ const startId = _get(state, ['startId']);
44
+ return _get(subState, ['current']) || startId;
45
+ },
46
+ makeSelectNodeErrors: (name) => (state) => {
47
+ const form = FlowerStateUtils.selectFlowerFormNode(name)(state);
48
+ return createFormData(form);
49
+ }
50
+ };
51
+ const createFormData = (form) => {
52
+ const validationErrors = form && form.errors;
53
+ const allErrors = Object.values(validationErrors || {});
54
+ return {
55
+ isSubmitted: form?.isSubmitted || false,
56
+ isDirty: Object.values(form?.dirty || {}).some(Boolean) || false,
57
+ hasFocus: form?.hasFocus,
58
+ errors: form?.errors,
59
+ customErrors: form?.customErrors,
60
+ isValidating: form?.isValidating,
61
+ isValid: allErrors.flat().length === 0
62
+ };
63
+ };
64
+
25
65
  const EMPTY_STRING_REGEXP = /^\s*$/;
26
66
  /**
27
67
  * Defines a utility object named rulesMatcherUtils, which contains various helper functions used for processing rules and data in a rule-matching context.
@@ -242,10 +282,6 @@ const rulesMatcher = (rules, formValue = {}, apply = true, options) => {
242
282
  const valid = rulesMatcherUtils.checkRule(conditions, formValue, options ?? {});
243
283
  return [valid === apply];
244
284
  };
245
- const MatchRules = {
246
- rulesMatcher,
247
- utils: rulesMatcherUtils
248
- };
249
285
 
250
286
  /* eslint-disable no-useless-escape */
251
287
  // TODO align this set of functions to selectors and reducers functions
@@ -268,36 +304,12 @@ const flattenRules = (ob) => {
268
304
  }
269
305
  return result;
270
306
  };
271
- // export const searchEmptyKeyRecursively = <T extends object>(
272
- // _key: "$and" | "$or",
273
- // obj: T
274
- // ) => {
275
- // if (
276
- // isEmpty(obj) ||
277
- // typeof obj !== "object" ||
278
- // Object.keys(obj).length === 0
279
- // ) {
280
- // return true;
281
- // }
282
- // if (Object.keys(obj).includes(_key)) {
283
- // if (obj[_key] && obj[_key].length === 0) return true;
284
- // return Object.keys(obj).map((key) =>
285
- // searchEmptyKeyRecursively(_key, obj[key])
286
- // );
287
- // }
288
- // return Object.keys(obj)
289
- // .map((key) => searchEmptyKeyRecursively(_key, obj[key]))
290
- // .every((v) => v === true);
291
- // };
292
307
  const getRulesExists = (rules) => {
293
- return Object.keys(rules).length ? CoreUtils.mapEdge(rules) : undefined;
308
+ return Object.keys(rules).length ? FlowUtils.mapEdge(rules) : undefined;
294
309
  };
295
- /**
296
- * Defines a collection of utility functions for processing rules, nodes and graph-like structures
297
- */
298
- const CoreUtils = {
310
+ const FlowUtils = {
299
311
  generateRulesName: (nextRules) => {
300
- const a = nextRules.reduce((acc, inc) => {
312
+ return nextRules.reduce((acc, inc) => {
301
313
  const n = typeof inc.rules === 'string'
302
314
  ? inc.rules || '__ERROR_NAME__'
303
315
  : inc.rules?.name || '__ERROR_NAME__';
@@ -306,7 +318,6 @@ const CoreUtils = {
306
318
  [n]: inc.nodeId
307
319
  };
308
320
  }, {});
309
- return a;
310
321
  },
311
322
  mapKeysDeepLodash: (obj, cb, isRecursive) => {
312
323
  /* istanbul ignore next */
@@ -322,13 +333,13 @@ const CoreUtils = {
322
333
  }
323
334
  }
324
335
  if (Array.isArray(obj)) {
325
- return obj.map((item) => CoreUtils.mapKeysDeepLodash(item, cb, true));
336
+ return obj.map((item) => FlowUtils.mapKeysDeepLodash(item, cb, true));
326
337
  }
327
338
  if (!isPlainObject(obj)) {
328
339
  return obj;
329
340
  }
330
341
  const result = mapKeys(obj, cb);
331
- return mapValues(result, (value) => CoreUtils.mapKeysDeepLodash(value, cb, true));
342
+ return mapValues(result, (value) => FlowUtils.mapKeysDeepLodash(value, cb, true));
332
343
  },
333
344
  generateNodes: (nodes) => keyBy(nodes.map((s) => omit(s, 'nextRules')), 'nodeId'),
334
345
  makeObjectRules: (nodes) => nodes.reduce((acc, inc) => ({ ...acc, [inc.nodeId]: inc.nextRules }), {}),
@@ -345,17 +356,18 @@ const CoreUtils = {
345
356
  },
346
357
  mapEdge: (nextNode) => {
347
358
  const res = nextNode.sort((a, b) => {
348
- const x = CoreUtils.isEmptyRules(a.rules);
349
- const y = CoreUtils.isEmptyRules(b.rules);
359
+ const x = FlowUtils.isEmptyRules(a.rules);
360
+ const y = FlowUtils.isEmptyRules(b.rules);
350
361
  return Number(x) - Number(y);
351
362
  });
352
363
  return res;
353
364
  },
354
365
  makeRules: (rules) => Object.entries(rules).reduce((acc2, [k, v]) => [...acc2, { nodeId: k, rules: v }], []),
366
+ // TODO: This function is strictly related to React nodes, could make sense to move it in the flower-react folder
355
367
  generateNodesForFlowerJson: (nodes) => nodes
356
368
  .filter((e) => !!_get(e, 'props.id'))
357
369
  .map((e) => {
358
- const rules = CoreUtils.makeRules(e.props.to ?? {});
370
+ const rules = FlowUtils.makeRules(e.props.to ?? {});
359
371
  const nextRules = getRulesExists(rules);
360
372
  const children = e.props.data?.children;
361
373
  return {
@@ -368,29 +380,6 @@ const CoreUtils = {
368
380
  disabled: e.props.disabled
369
381
  };
370
382
  }),
371
- cleanPath: (name, char = '^') => _trimStart(name, char),
372
- getPath: (idValue) => {
373
- if (!idValue) {
374
- return {
375
- path: []
376
- };
377
- }
378
- if (idValue === '*') {
379
- return {
380
- path: '*'
381
- };
382
- }
383
- if (idValue.indexOf('^') === 0) {
384
- const [flowNameFromPath, ...rest] = CoreUtils.cleanPath(idValue).split('.');
385
- return {
386
- flowNameFromPath,
387
- path: rest
388
- };
389
- }
390
- return {
391
- path: idValue.split('.')
392
- };
393
- },
394
383
  allEqual: (arr, arr2) => arr.length === arr2.length && arr.every((v) => arr2.includes(v)),
395
384
  findValidRule: (nextRules, value, prefix) => find(nextRules, (rule) => {
396
385
  // fix per evitare di entrare in un nodo senza regole, ma con un name,
@@ -410,53 +399,52 @@ const CoreUtils = {
410
399
  if (typeof rule.rules.rules === 'string') {
411
400
  return false;
412
401
  }
413
- const [valid] = MatchRules.rulesMatcher(rule.rules.rules, value, true, {
402
+ const [valid] = rulesMatcher(rule.rules.rules, value, true, {
414
403
  prefix
415
404
  });
416
405
  return valid;
417
406
  })
418
407
  };
419
408
 
420
- const FlowerStateUtils = {
421
- getAllData: (state) => state &&
422
- Object.entries(state ?? {}).reduce((acc, [k, v]) => ({ ...acc, [k]: v.data }), {}),
423
- selectFlowerFormNode: (name, id) => (state) => _get(state, [name, 'form', id]),
424
- makeSelectCurrentNextRules: (name) => (state) => {
425
- const nextRules = _get(state, [name, 'nextRules']);
426
- const currentNodeId = FlowerStateUtils.makeSelectCurrentNodeId(name)(state);
427
- return _get(nextRules, [currentNodeId]);
428
- },
429
- makeSelectCurrentNodeId: (name) => (state) => {
430
- const subState = _get(state, [name]);
431
- const startId = _get(state, ['startId']);
432
- return _get(subState, ['current']) || startId;
433
- },
434
- makeSelectNodeErrors: (name, currentNodeId) => (state) => {
435
- const form = FlowerStateUtils.selectFlowerFormNode(name, currentNodeId)(state);
436
- return createFormData(form);
409
+ const FormUtils = {
410
+ cleanPath: (name, char = '^') => _trimStart(name, char),
411
+ getPath: (idValue) => {
412
+ if (!idValue) {
413
+ return {
414
+ path: []
415
+ };
416
+ }
417
+ if (idValue === '*') {
418
+ return {
419
+ path: '*'
420
+ };
421
+ }
422
+ if (idValue.indexOf('^') === 0) {
423
+ const [formName, ...rest] = FormUtils.cleanPath(idValue).split('.');
424
+ return {
425
+ formName,
426
+ path: rest
427
+ };
428
+ }
429
+ return {
430
+ path: idValue.split('.')
431
+ };
437
432
  }
438
433
  };
439
- const createFormData = (form) => {
440
- const validationErrors = form && form.errors;
441
- const allErrors = Object.values(validationErrors || {});
442
- return {
443
- isSubmitted: form?.isSubmitted || false,
444
- isDirty: form?.isDirty || false,
445
- hasFocus: form?.hasFocus,
446
- errors: form?.errors,
447
- customErrors: form?.customErrors,
448
- isValidating: form?.isValidating,
449
- isValid: allErrors.flat().length === 0
450
- };
451
- };
452
434
 
453
- const devtoolState = {};
435
+ /**
436
+ * Defines a collection of utility functions for processing rules, nodes and graph-like structures
437
+ */
438
+ const CoreUtils = {
439
+ ...FlowUtils,
440
+ ...FormUtils
441
+ };
454
442
 
455
- const { generateNodes, hasNode, makeObjectRules, generateRulesName, findValidRule, getPath } = CoreUtils;
443
+ const { generateNodes, hasNode, makeObjectRules, generateRulesName, findValidRule } = CoreUtils;
456
444
  /**
457
445
  * These functions are Redux reducers used in a Flux architecture for managing state transitions and updates in a Flower application.
458
446
  */
459
- const FlowerCoreReducers = {
447
+ const FlowerCoreBaseReducers = {
460
448
  historyAdd: (state, { payload }) => {
461
449
  if (hasNode(state, payload.name, payload.node)) {
462
450
  state[payload.name].history.push(payload.node);
@@ -475,27 +463,11 @@ const FlowerCoreReducers = {
475
463
  }
476
464
  return state;
477
465
  },
478
- setFormTouched: (state, { payload }) => {
479
- if (!_get(state, [
480
- typeof payload === 'string' ? payload : payload.flowName,
481
- 'nodes',
482
- typeof payload === 'string' ? payload : payload.currentNode
483
- ])) {
484
- return state;
485
- }
486
- _set(state, [
487
- typeof payload === 'string' ? payload : payload.flowName,
488
- 'form',
489
- typeof payload === 'string' ? payload : payload.currentNode,
490
- 'isSubmitted'
491
- ], true);
492
- return state;
493
- },
494
466
  // TODO check internal logic and use case
495
467
  /* istanbul ignore next */
496
468
  forceAddHistory: (state, { payload }) => {
497
469
  const { name, flowName, history } = payload;
498
- const key = name || flowName || '' || '';
470
+ const key = name || flowName || '';
499
471
  const resultHistory = history.slice(1, -1);
500
472
  state[key].history.push(...resultHistory);
501
473
  return state;
@@ -568,7 +540,8 @@ const FlowerCoreReducers = {
568
540
  return state;
569
541
  },
570
542
  destroy: (state, { payload }) => {
571
- _set(state, [payload.name], {});
543
+ delete state[payload.name];
544
+ return state;
572
545
  },
573
546
  initNodes: (state, { payload }) => {
574
547
  if (payload.persist && _get(state, [payload.name, 'persist']))
@@ -591,8 +564,7 @@ const FlowerCoreReducers = {
591
564
  current,
592
565
  history,
593
566
  nodes: generateNodes(payload.nodes),
594
- nextRules: makeObjectRules(payload.nodes),
595
- data: payload.initialData
567
+ nextRules: makeObjectRules(payload.nodes)
596
568
  });
597
569
  },
598
570
  // TODO usato solo da flower su vscode
@@ -609,105 +581,14 @@ const FlowerCoreReducers = {
609
581
  }
610
582
  }
611
583
  },
612
- formAddCustomErrors: (state, { payload }) => {
613
- _set(state, [payload.name, 'form', payload.currentNode, 'customErrors', payload.id], payload.errors);
614
- },
615
- formAddErrors: (state, { payload }) => {
616
- _set(state, [payload.name, 'form', payload.currentNode, 'errors', payload.id], payload.errors);
617
- },
618
- formRemoveErrors: (state, { payload }) => {
619
- _unset(state, [
620
- payload.name,
621
- 'form',
622
- payload.currentNode,
623
- 'errors',
624
- payload.id
625
- ]);
626
- _unset(state, [
627
- payload.name,
628
- 'form',
629
- payload.currentNode,
630
- 'customErrors',
631
- payload.id
632
- ]);
633
- _unset(state, [payload.name, 'form', payload.currentNode, 'isValidating']);
634
- },
635
- formFieldTouch: (state, { payload }) => {
636
- _set(state, [payload.name, 'form', payload.currentNode, 'touches', payload.id], payload.touched);
637
- },
638
- formFieldFocus: (state, { payload }) => {
639
- if (!payload.focused) {
640
- _unset(state, [payload.name, 'form', payload.currentNode, 'hasFocus']);
641
- return;
642
- }
643
- _set(state, [payload.name, 'form', payload.currentNode, 'hasFocus'], payload.id);
644
- },
645
- addData: (state, { payload }) => {
646
- const prevData = _get(state, [payload.flowName, 'data']);
647
- _set(state, [payload.flowName, 'data'], { ...prevData, ...payload.value });
648
- },
649
- addDataByPath: (state, { payload }) => {
650
- const { path: newpath } = getPath(payload.id);
651
- const currentNode = FlowerStateUtils.makeSelectCurrentNodeId(payload.flowName)(state);
652
- if (payload.id && payload.id.length) {
653
- _set(state, [payload.flowName, 'data', ...newpath], payload.value);
654
- if (payload && payload.dirty) {
655
- _set(state, [payload.flowName, 'form', currentNode, 'dirty', payload.id], payload.dirty);
656
- _set(state, [payload.flowName, 'form', currentNode, 'isDirty'], true);
657
- }
658
- }
659
- },
660
- // TODO usato al momento solo il devtool
661
- replaceData: /* istanbul ignore next */ (state, { payload }) => {
662
- /* istanbul ignore next */
663
- _set(state, [payload.flowName, 'data'], payload.value);
664
- },
665
- unsetData: (state, { payload }) => {
666
- const currentNode = FlowerStateUtils.makeSelectCurrentNodeId(payload.flowName)(state);
667
- _unset(state, [
668
- payload.flowName,
669
- 'form',
670
- currentNode,
671
- 'dirty',
672
- ...payload.id
673
- ]);
674
- _unset(state, [
675
- payload.flowName,
676
- 'form',
677
- currentNode,
678
- 'touches',
679
- ...payload.id
680
- ]);
681
- _unset(state, [payload.flowName, 'data', ...payload.id]);
682
- },
683
- setFormIsValidating: (state, { payload }) => {
684
- _set(state, [payload.name, 'form', payload.currentNode, 'isValidating'], payload.isValidating);
685
- },
686
- resetForm: (state, { payload }) => {
687
- const touchedFields = _get(state, [payload.flowName, 'form', payload.id, 'errors'], {});
688
- Object.keys(touchedFields).forEach((key) => {
689
- const { flowNameFromPath = payload.flowName, path } = getPath(key);
690
- _unset(state, [flowNameFromPath, 'data', ...path]);
691
- });
692
- _unset(state, [payload.flowName, 'form', payload.id, 'touches']);
693
- _unset(state, [payload.flowName, 'form', payload.id, 'dirty']);
694
- _unset(state, [payload.flowName, 'form', payload.id, 'isDirty']);
695
- _unset(state, [payload.flowName, 'form', payload.id, 'isSubmitted']);
696
- },
697
584
  node: (state, { payload }) => {
698
585
  const { name, history } = payload;
699
586
  const node = payload.nodeId || payload.node || '';
700
587
  const flowName = name || payload.flowName || '';
701
- const startNode = _get(state, [payload.name, 'startId']);
702
- const currentNodeId = _get(state, [payload.name, 'current'], startNode);
703
- FlowerCoreReducers.setFormTouched(state, {
704
- type: 'setFormTouched',
705
- payload: { flowName, currentNode: currentNodeId }
706
- });
707
588
  /* istanbul ignore next */
708
589
  // eslint-disable-next-line no-underscore-dangle
709
590
  if (devtoolState && _get(devtoolState, '__FLOWER_DEVTOOLS__') && history) {
710
- FlowerCoreReducers.forceAddHistory(state, {
591
+ FlowerCoreBaseReducers.forceAddHistory(state, {
711
592
  type: 'forceAddHistory',
712
593
  payload: {
713
594
  name,
@@ -716,34 +597,35 @@ const FlowerCoreReducers = {
716
597
  }
717
598
  });
718
599
  }
719
- FlowerCoreReducers.historyAdd(state, {
600
+ FlowerCoreBaseReducers.historyAdd(state, {
720
601
  type: 'historyAdd',
721
602
  payload: { name: name || flowName || '', node }
722
603
  });
723
604
  },
724
605
  prevToNode: (state, { payload }) => {
725
606
  const { node, name, flowName } = payload;
726
- FlowerCoreReducers.historyPrevToNode(state, {
607
+ FlowerCoreBaseReducers.historyPrevToNode(state, {
727
608
  type: 'historyPrevToNode',
728
609
  payload: { name: name || flowName || '', node }
729
610
  });
730
611
  },
731
612
  next: (state, { payload }) => {
732
- const { name, data = {}, route } = payload;
733
- const flowName = name || payload.flowName || '';
613
+ const { name, route, flowName: flow, data = {}, dataIn = {} } = payload;
614
+ const flowName = name || flow || '';
615
+ const { FlowerData, FlowerFlow, ...external } = data;
734
616
  const currentNodeId = FlowerStateUtils.makeSelectCurrentNodeId(flowName)(state);
735
617
  const currentNextRules = FlowerStateUtils.makeSelectCurrentNextRules(flowName)(state);
736
- const form = FlowerStateUtils.makeSelectNodeErrors(flowName, currentNodeId)(state);
737
- const clonedData = _cloneDeep(FlowerStateUtils.getAllData(state));
618
+ const $data = FlowerStateUtils.makeSelectNodeErrors(flowName, currentNodeId)(FlowerData);
619
+ const internalClonedData = _cloneDeep(FlowerStateUtils.getAllData(FlowerData));
620
+ const externalClonedData = _cloneDeep(FlowerStateUtils.getAllData(external));
738
621
  const stateWithNodeData = {
739
- $in: data,
740
- $form: form,
741
- ...clonedData
622
+ $in: dataIn,
623
+ /** @deprecated use $data instead */
624
+ $form: $data,
625
+ $data,
626
+ ...externalClonedData,
627
+ ...internalClonedData
742
628
  };
743
- FlowerCoreReducers.setFormTouched(state, {
744
- type: 'setFormTouched',
745
- payload: { flowName, currentNode: currentNodeId }
746
- });
747
629
  if (!currentNextRules) {
748
630
  return;
749
631
  }
@@ -752,7 +634,7 @@ const FlowerCoreReducers = {
752
634
  if (!rulesByName[route]) {
753
635
  return;
754
636
  }
755
- FlowerCoreReducers.historyAdd(state, {
637
+ FlowerCoreBaseReducers.historyAdd(state, {
756
638
  type: 'historyAdd',
757
639
  payload: { name: flowName, node: rulesByName[route] }
758
640
  });
@@ -763,51 +645,132 @@ const FlowerCoreReducers = {
763
645
  if (!nextNumberNode) {
764
646
  return;
765
647
  }
766
- FlowerCoreReducers.historyAdd(state, {
648
+ FlowerCoreBaseReducers.historyAdd(state, {
767
649
  type: 'historyAdd',
768
650
  payload: { name: flowName, node: nextNumberNode }
769
651
  });
770
652
  },
771
653
  prev: (state, { payload }) => {
772
654
  const { name, flowName } = payload;
773
- FlowerCoreReducers.historyPop(state, {
655
+ FlowerCoreBaseReducers.historyPop(state, {
774
656
  type: 'historyPop',
775
657
  payload: { name: name || flowName || '' }
776
658
  });
777
659
  },
778
660
  restart: (state, { payload }) => {
779
661
  const { name, flowName } = payload;
780
- FlowerCoreReducers.restoreHistory(state, {
662
+ FlowerCoreBaseReducers.restoreHistory(state, {
781
663
  type: 'restoreHistory',
782
664
  payload: { name: name || flowName || '' }
783
665
  });
784
666
  },
785
667
  reset: (state, { payload }) => {
786
- const { name, flowName, initialData } = payload;
787
- FlowerCoreReducers.restoreHistory(state, {
668
+ const { name, flowName } = payload;
669
+ FlowerCoreBaseReducers.restoreHistory(state, {
788
670
  type: 'restoreHistory',
789
671
  payload: { name: name || flowName || '' }
790
672
  });
791
- _set(state, [name || flowName || '', 'form'], {});
792
- _set(state, [name || flowName || '', 'data'], initialData);
793
673
  }
794
674
  };
795
675
 
796
- const FlowerCoreStateSelectors = {
797
- selectGlobal: (state) => state && state.flower,
676
+ const { getPath } = CoreUtils;
677
+ /**
678
+ * formName => FlowerForm
679
+ * initialData => FlowerForm
680
+ * fieldName => FlowerField
681
+ * fieldValue => FlowerField
682
+ * errors => FlowerField
683
+ * customErrors => FlowerField
684
+ * fieldTouched => FlowerField
685
+ * fieldDirty => FlowerField
686
+ * fieldHasFocus => FlowerField
687
+ */
688
+ const FlowerCoreDataReducers = {
689
+ setFormTouched: (state, { payload }) => {
690
+ if (!_get(state, typeof payload === 'string' ? payload : payload.formName)) {
691
+ return state;
692
+ }
693
+ _set(state, typeof payload === 'string' ? payload : payload.formName, true);
694
+ return state;
695
+ },
696
+ formAddCustomErrors: (state, { payload }) => {
697
+ _set(state, [payload.formName, 'customErrors', payload.id], payload.errors);
698
+ },
699
+ formAddErrors: (state, { payload }) => {
700
+ _set(state, [payload.formName, 'errors', payload.id], payload.errors);
701
+ },
702
+ formRemoveErrors: (state, { payload }) => {
703
+ _unset(state, [payload.formName, 'errors', payload.id]);
704
+ _unset(state, [payload.formName, 'customErrors', payload.id]);
705
+ _unset(state, [payload.formName, 'isValidating']);
706
+ },
707
+ formFieldTouch: (state, { payload }) => {
708
+ _set(state, [payload.formName, 'touches', payload.id], payload.touched);
709
+ },
710
+ formFieldDirty: (state, { payload }) => {
711
+ _set(state, [payload.formName, 'dirty', payload.id], payload.dirty);
712
+ },
713
+ formFieldFocus: (state, { payload }) => {
714
+ if (!payload.focused) {
715
+ _unset(state, [payload.formName, 'hasFocus']);
716
+ return;
717
+ }
718
+ _set(state, [payload.formName, 'hasFocus'], payload.id);
719
+ },
720
+ addData: (state, { payload }) => {
721
+ const prevData = _get(state, [payload.formName, 'data'], {});
722
+ _set(state, [payload.formName, 'data'], { ...prevData, ...payload.value });
723
+ },
724
+ addDataByPath: (state, { payload }) => {
725
+ const { path: newpath } = getPath(payload.id);
726
+ if (payload.id && payload.id.length) {
727
+ _set(state, [payload.formName, 'data', ...newpath], payload.value);
728
+ if (payload && payload.dirty) {
729
+ _set(state, [payload.formName, 'dirty', payload.id], payload.dirty);
730
+ }
731
+ }
732
+ },
733
+ // TODO usato al momento solo il devtool
734
+ replaceData: /* istanbul ignore next */ (state, { payload }) => {
735
+ /* istanbul ignore next */
736
+ _set(state, [payload.formName, 'data'], payload.value);
737
+ },
738
+ unsetData: (state, { payload }) => {
739
+ _unset(state, [payload.formName, 'data', ...payload.id]);
740
+ },
741
+ setFormIsValidating: (state, { payload }) => {
742
+ _set(state, [payload.formName, 'isValidating'], payload.isValidating);
743
+ },
744
+ resetForm: (state, { payload: { formName, initialData } }) => {
745
+ const touchedFields = _get(state, [formName, 'errors'], {});
746
+ const newStateData = initialData
747
+ ? Object.keys(touchedFields).reduce((acc, key) => {
748
+ const { path } = getPath(key);
749
+ const initialDataByPath = _get(initialData, [...path], undefined);
750
+ _set(acc, [...path], initialDataByPath);
751
+ return acc;
752
+ }, {})
753
+ : {};
754
+ _set(state, [formName, 'data'], newStateData);
755
+ _unset(state, [formName, 'touches']);
756
+ _unset(state, [formName, 'dirty']);
757
+ _unset(state, [formName, 'isSubmitted']);
758
+ },
759
+ initForm: (state, { payload: { formName, initialData } }) => {
760
+ _set(state, [formName, 'data'], initialData);
761
+ }
762
+ };
763
+
764
+ const FlowerCoreReducers = { ...FlowerCoreBaseReducers, ...FlowerCoreDataReducers };
765
+
766
+ const FlowerCoreStateBaseSelectors = {
767
+ selectGlobal: (state) => state && state[exports.REDUCER_NAME.FLOWER_FLOW],
798
768
  selectFlower: (name) => (state) => _get(state, [name]),
799
- selectFlowerFormNode: (id) => (state) => _get(state, ['form', id]),
769
+ // selectFlowerFormNode: (id) => (state) =>
770
+ // _get(state, [REDUCER_NAME.FLOWER_DATA, id]),
800
771
  selectFlowerHistory: (flower) => _get(flower, ['history'], []),
801
772
  makeSelectNodesIds: (flower) => _get(flower, ['nodes']),
802
773
  makeSelectStartNodeId: (flower) => _get(flower, ['startId']),
803
- getDataByFlow: (flower) => _get(flower, ['data']) ?? {},
804
- getDataFromState: (id) => (data) => (id === '*' ? data : _get(data, id)),
805
- makeSelectNodeFormSubmitted: (form) => form && form.isSubmitted,
806
- makeSelectNodeFormFieldTouched: (id) => (form) => form && form.touches && form.touches[id],
807
- makeSelectNodeFormFieldFocused: (id) => (form) => {
808
- return form && form.hasFocus === id ? id : undefined;
809
- },
810
- makeSelectNodeFormFieldDirty: (id) => (form) => form && form.dirty && form.dirty[id],
811
774
  makeSelectCurrentNodeId: (flower, startNodeId) => _get(flower, ['current']) || startNodeId,
812
775
  makeSelectCurrentNodeDisabled: (nodes, current) => !!_get(nodes, [current, 'disabled']),
813
776
  makeSelectPrevNodeRetain: (nodes, history, current) => {
@@ -828,7 +791,22 @@ const FlowerCoreStateSelectors = {
828
791
  return nodes[prevFlowerNode] && nodes[prevFlowerNode].retain
829
792
  ? prevFlowerNode
830
793
  : undefined;
794
+ }
795
+ };
796
+
797
+ const FlowerCoreStateDataSelectors = {
798
+ selectGlobalReducerByName: (name) => (state) => state[name] ?? state[exports.REDUCER_NAME.FLOWER_DATA][name],
799
+ selectGlobalForm: (state) => {
800
+ return state && state[exports.REDUCER_NAME.FLOWER_DATA];
831
801
  },
802
+ // getDataByFlow: (flower) => _get(flower, 'data') ?? {},
803
+ getDataFromState: (id) => (data) => (id === '*' ? data : _get(data, id)),
804
+ makeSelectNodeFormSubmitted: (form) => form && form.isSubmitted,
805
+ makeSelectNodeFormFieldTouched: (id) => (form) => form && form.touches && form.touches[id],
806
+ makeSelectNodeFormFieldFocused: (id) => (form) => {
807
+ return form && form.hasFocus === id ? id : undefined;
808
+ },
809
+ makeSelectNodeFormFieldDirty: (id) => (form) => form && form.dirty && form.dirty[id],
832
810
  makeSelectNodeErrors: createFormData,
833
811
  makeSelectFieldError: (name, id, validate) => (data, form) => {
834
812
  const customErrors = Object.entries((form && form.customErrors) || {})
@@ -843,7 +821,7 @@ const FlowerCoreStateSelectors = {
843
821
  if (!rule.rules)
844
822
  return true;
845
823
  const transformSelf = CoreUtils.mapKeysDeepLodash(rule.rules, (v, key) => key === '$self' ? id : key);
846
- const [hasError] = MatchRules.rulesMatcher(transformSelf, data, false, {
824
+ const [hasError] = rulesMatcher(transformSelf, data, false, {
847
825
  prefix: name
848
826
  });
849
827
  return hasError;
@@ -865,39 +843,31 @@ const FlowerCoreStateSelectors = {
865
843
  const k = inc;
866
844
  return Object.assign(acc, { [k]: _get(state, k) });
867
845
  }, {});
868
- const [disabled] = MatchRules.rulesMatcher(rules, { ...flat.unflatten(res) }, false, { prefix: flowName });
846
+ const [disabled] = rulesMatcher(rules, { ...flat.unflatten(res) }, false, {
847
+ prefix: flowName
848
+ });
869
849
  return disabled;
870
850
  }
871
851
  };
872
852
 
873
- exports.RulesOperators = void 0;
874
- (function (RulesOperators) {
875
- RulesOperators["$exists"] = "$exists";
876
- RulesOperators["$eq"] = "$eq";
877
- RulesOperators["$ne"] = "$ne";
878
- RulesOperators["$gt"] = "$gt";
879
- RulesOperators["$gte"] = "$gte";
880
- RulesOperators["$lt"] = "$lt";
881
- RulesOperators["$lte"] = "$lte";
882
- RulesOperators["$strGt"] = "$strGt";
883
- RulesOperators["$strGte"] = "$strGte";
884
- RulesOperators["$strLt"] = "$strLt";
885
- RulesOperators["$strLte"] = "$strLte";
886
- RulesOperators["$in"] = "$in";
887
- RulesOperators["$nin"] = "$nin";
888
- RulesOperators["$all"] = "$all";
889
- RulesOperators["$regex"] = "$regex";
890
- })(exports.RulesOperators || (exports.RulesOperators = {}));
891
- exports.RulesModes = void 0;
892
- (function (RulesModes) {
893
- RulesModes["$and"] = "$and";
894
- RulesModes["$or"] = "$or";
895
- })(exports.RulesModes || (exports.RulesModes = {}));
853
+ const FlowerCoreStateSelectors = {
854
+ ...FlowerCoreStateBaseSelectors,
855
+ ...FlowerCoreStateDataSelectors
856
+ };
896
857
 
897
858
  exports.CoreUtils = CoreUtils;
898
859
  exports.Emitter = Emitter;
860
+ exports.FlowUtils = FlowUtils;
861
+ exports.FlowerCoreBaseReducers = FlowerCoreBaseReducers;
862
+ exports.FlowerCoreDataReducers = FlowerCoreDataReducers;
899
863
  exports.FlowerCoreReducers = FlowerCoreReducers;
864
+ exports.FlowerCoreStateBaseSelectors = FlowerCoreStateBaseSelectors;
865
+ exports.FlowerCoreStateDataSelectors = FlowerCoreStateDataSelectors;
866
+ exports.FlowerCoreStateSelectors = FlowerCoreStateSelectors;
900
867
  exports.FlowerStateUtils = FlowerStateUtils;
901
- exports.MatchRules = MatchRules;
902
- exports.Selectors = FlowerCoreStateSelectors;
868
+ exports.FormUtils = FormUtils;
869
+ exports.createFormData = createFormData;
903
870
  exports.devtoolState = devtoolState;
871
+ exports.flattenRules = flattenRules;
872
+ exports.rulesMatcher = rulesMatcher;
873
+ exports.rulesMatcherUtils = rulesMatcherUtils;