tinybase 9.4.0-beta.0 → 9.4.0-beta.1

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.
@@ -53,6 +53,7 @@ const arrayEvery = (array, cb) => array.every(cb);
53
53
  const arrayIsEqual = (array1, array2) =>
54
54
  size(array1) === size(array2) &&
55
55
  arrayEvery(array1, (value1, index) => array2[index] === value1);
56
+ const arraySort = (array, sorter) => array.sort(sorter);
56
57
  const arrayForEach = (array, cb) => array.forEach(cb);
57
58
  const arraySum = (array) => arrayReduce(array, (i, j) => i + j, 0);
58
59
  const arrayMax = (array) =>
@@ -111,6 +112,10 @@ const objNew = (entries = []) => {
111
112
  arrayForEach(entries, ([id, value]) => objSet(obj, id, value));
112
113
  return obj;
113
114
  };
115
+ const objDel = (obj, id) => {
116
+ delete obj[id];
117
+ return obj;
118
+ };
114
119
  const objForEach = (obj, cb) =>
115
120
  arrayForEach(objIds(obj), (id) => cb(obj[id], id));
116
121
  const objSize = (obj) => size(objIds(obj));
@@ -464,6 +469,8 @@ const createQueries = getCreateFunction((store) => {
464
469
  };
465
470
  const preStoreListenerIds = mapNew();
466
471
  const sourceStoreListenerIds = mapNew();
472
+ const selectAllListenerIds = mapNew();
473
+ const referencedQueryIds = mapNew();
467
474
  const {
468
475
  _: [, addListener, callListeners],
469
476
  delListener: delListenerImpl,
@@ -537,11 +544,42 @@ const createQueries = getCreateFunction((store) => {
537
544
  resetStoreListeners(mapGet(sourceStoreListenerIds, queryId));
538
545
  mapSet(sourceStoreListenerIds, queryId);
539
546
  };
540
- const isResultStoreReferenced = (resultStore2) =>
547
+ const syncSelectAllListeners = (queryId, nextSources = mapNew()) => {
548
+ const listenerIds = mapEnsure(selectAllListenerIds, queryId, mapNew);
549
+ mapForEach(listenerIds, (sourceStore, listenerIdsByTableId) => {
550
+ mapForEach(listenerIdsByTableId, (sourceTableId, listenerId) =>
551
+ collHas(mapGet(nextSources, sourceStore), sourceTableId)
552
+ ? 0
553
+ : (sourceStore.delListener(listenerId),
554
+ mapSet(listenerIdsByTableId, sourceTableId)),
555
+ );
556
+ if (collIsEmpty(listenerIdsByTableId)) {
557
+ mapSet(listenerIds, sourceStore);
558
+ }
559
+ });
560
+ mapForEach(nextSources, (sourceStore, tableIds) => {
561
+ const listenerIdsByTableId = mapEnsure(listenerIds, sourceStore, mapNew);
562
+ collForEach(tableIds, (sourceTableId) =>
563
+ mapEnsure(listenerIdsByTableId, sourceTableId, () =>
564
+ sourceStore.addTableCellIdsListener(sourceTableId, () =>
565
+ setQueryDefinitionImpl(queryId),
566
+ ),
567
+ ),
568
+ );
569
+ });
570
+ if (collIsEmpty(listenerIds)) {
571
+ mapSet(selectAllListenerIds, queryId);
572
+ }
573
+ };
574
+ const isResultStoreReferenced = (queryId, resultStore2) =>
541
575
  !(
542
576
  collEvery(routedResultListeners, ([, storeListenerIds]) =>
543
577
  collEvery(storeListenerIds, ([store2]) => store2 !== resultStore2),
544
578
  ) &&
579
+ collEvery(
580
+ referencedQueryIds,
581
+ (queryIds) => !collHas(queryIds, queryId),
582
+ ) &&
545
583
  arrayEvery(
546
584
  [preStoreListenerIds, sourceStoreListenerIds],
547
585
  (storeListenerIds) =>
@@ -556,7 +594,7 @@ const createQueries = getCreateFunction((store) => {
556
594
  hasQuery(queryId) ? 0 : mapSet(preStores, queryId),
557
595
  );
558
596
  mapForEach(resultStores, (queryId, resultStore2) =>
559
- hasQuery(queryId) || isResultStoreReferenced(resultStore2)
597
+ hasQuery(queryId) || isResultStoreReferenced(queryId, resultStore2)
560
598
  ? 0
561
599
  : mapSet(resultStores, queryId),
562
600
  );
@@ -638,7 +676,13 @@ const createQueries = getCreateFunction((store) => {
638
676
  const rootStore = asQuery ? getResultStore(tableId) : store;
639
677
  const resultStore2 = getResultStore(queryId);
640
678
  const paramValues = definition?.[3] ?? getParamValues(queryId);
641
- const selectEntries = [];
679
+ const nextReferencedQueryIds = stagedDefinition[4];
680
+ if (asQuery) {
681
+ setAdd(nextReferencedQueryIds, tableId);
682
+ }
683
+ const selectionEntries = [];
684
+ let hasSelectAll = false;
685
+ let selectCount = 0;
642
686
  const joinEntries = [
643
687
  [void 0, [tableId, void 0, void 0, [], mapNew(), rootStore]],
644
688
  ];
@@ -650,21 +694,35 @@ const createQueries = getCreateFunction((store) => {
650
694
  const joinedTableId = isTrue(arg1) ? arg2 : arg1;
651
695
  const joinedCellId = isTrue(arg1) ? arg3 : arg2;
652
696
  const selectEntry = isFunction(arg1)
653
- ? [size(selectEntries) + EMPTY_STRING, arg1]
697
+ ? [0, selectCount + EMPTY_STRING, arg1]
654
698
  : isUndefined(joinedCellId)
655
- ? [arg1, (getTableCell) => getTableCell(arg1)]
699
+ ? [0, arg1, (getTableCell) => getTableCell(arg1)]
656
700
  : [
701
+ 0,
657
702
  joinedCellId,
658
703
  (getTableCell) =>
659
704
  isTrue(arg1)
660
705
  ? getTableCell(true, joinedTableId, joinedCellId)
661
706
  : getTableCell(joinedTableId, joinedCellId),
662
707
  ];
663
- arrayPush(selectEntries, selectEntry);
708
+ selectCount++;
709
+ arrayPush(selectionEntries, selectEntry);
664
710
  return {
665
- as: (selectedCellId) => (selectEntry[0] = selectedCellId),
711
+ as: (selectedCellId) => (selectEntry[1] = selectedCellId),
666
712
  };
667
713
  };
714
+ const selectAll = (arg1, arg2, arg3) => {
715
+ hasSelectAll = true;
716
+ const joinedTableId = isTrue(arg1) ? arg2 : arg1;
717
+ const prefixOrMapper = isTrue(arg1) ? arg3 : arg2;
718
+ arrayPush(selectionEntries, [
719
+ 1,
720
+ joinedTableId,
721
+ isFunction(prefixOrMapper)
722
+ ? prefixOrMapper
723
+ : (cellId) => (prefixOrMapper ?? EMPTY_STRING) + cellId,
724
+ ]);
725
+ };
668
726
  const join = (arg1, arg2, arg3, arg4) => {
669
727
  const joinedTableId = isTrue(arg1) ? arg2 : arg1;
670
728
  const [fromJoinAlias, onArg] = isTrue(arg1)
@@ -674,6 +732,13 @@ const createQueries = getCreateFunction((store) => {
674
732
  : isUndefined(arg3) || isFunction(arg2)
675
733
  ? [void 0, arg2]
676
734
  : [arg2, arg3];
735
+ const sourceIsQuery = isTrue(arg1);
736
+ const sourceStore = sourceIsQuery
737
+ ? getResultStore(joinedTableId)
738
+ : store;
739
+ if (sourceIsQuery) {
740
+ setAdd(nextReferencedQueryIds, joinedTableId);
741
+ }
677
742
  const joinEntry = [
678
743
  joinedTableId,
679
744
  [
@@ -682,7 +747,7 @@ const createQueries = getCreateFunction((store) => {
682
747
  isFunction(onArg) ? onArg : (getCell) => getCell(onArg),
683
748
  [],
684
749
  mapNew(),
685
- isTrue(arg1) ? getResultStore(joinedTableId) : store,
750
+ sourceStore,
686
751
  ],
687
752
  ];
688
753
  arrayPush(joinEntries, joinEntry);
@@ -728,10 +793,9 @@ const createQueries = getCreateFunction((store) => {
728
793
  : (getSelectedOrGroupedCell) =>
729
794
  getSelectedOrGroupedCell(arg1) === arg2,
730
795
  );
731
- build({select, join, where, group, having, param});
796
+ build({select, selectAll, join, where, group, having, param});
732
797
  resultStore2.delTable(queryId);
733
- const selects = mapNew(selectEntries);
734
- if (collIsEmpty(selects)) {
798
+ if (isEmpty(selectionEntries)) {
735
799
  commit?.();
736
800
  return queries;
737
801
  }
@@ -743,6 +807,55 @@ const createQueries = getCreateFunction((store) => {
743
807
  );
744
808
  const groups = mapNew(groupEntries);
745
809
  const hasGroupsOrHavings = !collIsEmpty(groups) || !isEmpty(havings);
810
+ const selectEntries = [];
811
+ const selectAllSources = stagedDefinition[3];
812
+ const getSelectAllJoin = (joinedTableId) =>
813
+ mapGet(
814
+ joins,
815
+ isUndefined(joinedTableId) || joinedTableId === tableId
816
+ ? void 0
817
+ : joinedTableId,
818
+ );
819
+ arrayForEach(
820
+ selectionEntries,
821
+ ([selectAll2, selectedOrJoinedTableId, clauseOrMapper]) => {
822
+ if (selectAll2) {
823
+ if (hasGroupsOrHavings) {
824
+ ifNotUndefined(
825
+ getSelectAllJoin(selectedOrJoinedTableId),
826
+ ([realTableId, , , , , sourceStore]) => {
827
+ setAdd(
828
+ mapEnsure(selectAllSources, sourceStore, setNew),
829
+ realTableId,
830
+ );
831
+ arrayForEach(
832
+ arraySort(sourceStore.getTableCellIds(realTableId)),
833
+ (cellId) =>
834
+ arrayPush(selectEntries, [
835
+ clauseOrMapper(cellId),
836
+ (getTableCell) =>
837
+ isUndefined(selectedOrJoinedTableId) ||
838
+ selectedOrJoinedTableId === tableId
839
+ ? getTableCell(cellId)
840
+ : getTableCell(selectedOrJoinedTableId, cellId),
841
+ ]),
842
+ );
843
+ },
844
+ );
845
+ }
846
+ } else {
847
+ arrayPush(selectEntries, [
848
+ selectedOrJoinedTableId,
849
+ clauseOrMapper,
850
+ ]);
851
+ }
852
+ },
853
+ );
854
+ const selects = mapNew(selectEntries);
855
+ if (hasGroupsOrHavings && collIsEmpty(selects)) {
856
+ commit?.();
857
+ return queries;
858
+ }
746
859
  const selectJoinWhereStore = hasGroupsOrHavings
747
860
  ? (stagedDefinition[2] = createStore())
748
861
  : resultStore2;
@@ -921,18 +1034,78 @@ const createQueries = getCreateFunction((store) => {
921
1034
  joinedCellId,
922
1035
  );
923
1036
  };
924
- selectJoinWhereStore.transaction(() =>
925
- arrayEvery(wheres, (where2) => where2(getJoinCell))
926
- ? mapForEach(selects, (asCellId, tableCellGetter) =>
927
- selectJoinWhereStore._[5](
928
- queryId,
929
- rootRowId,
930
- asCellId,
931
- tableCellGetter(getJoinCell, rootRowId),
932
- ),
933
- )
934
- : selectJoinWhereStore.delRow(queryId, rootRowId),
935
- );
1037
+ selectJoinWhereStore.transaction(() => {
1038
+ if (!arrayEvery(wheres, (where2) => where2(getJoinCell))) {
1039
+ selectJoinWhereStore.delRow(queryId, rootRowId);
1040
+ } else if (hasGroupsOrHavings) {
1041
+ mapForEach(selects, (asCellId, tableCellGetter) =>
1042
+ selectJoinWhereStore._[5](
1043
+ queryId,
1044
+ rootRowId,
1045
+ asCellId,
1046
+ tableCellGetter(getJoinCell, rootRowId),
1047
+ ),
1048
+ );
1049
+ } else if (hasSelectAll) {
1050
+ const resultRow = objNew();
1051
+ arrayForEach(
1052
+ selectionEntries,
1053
+ ([selectAll2, selectedOrJoinedTableId, clauseOrMapper]) => {
1054
+ if (selectAll2) {
1055
+ ifNotUndefined(
1056
+ getSelectAllJoin(selectedOrJoinedTableId),
1057
+ ([realTableId, , , , remoteIdPairs, sourceStore]) => {
1058
+ const sourceRowId =
1059
+ isUndefined(selectedOrJoinedTableId) ||
1060
+ selectedOrJoinedTableId === tableId
1061
+ ? rootRowId
1062
+ : mapGet(remoteIdPairs, rootRowId)?.[0];
1063
+ ifNotUndefined(sourceRowId, (sourceRowId2) =>
1064
+ arrayForEach(
1065
+ arraySort(
1066
+ sourceStore.getCellIds(realTableId, sourceRowId2),
1067
+ ),
1068
+ (cellId) =>
1069
+ objSet(
1070
+ resultRow,
1071
+ clauseOrMapper(cellId),
1072
+ sourceStore.getCell(
1073
+ realTableId,
1074
+ sourceRowId2,
1075
+ cellId,
1076
+ ),
1077
+ ),
1078
+ ),
1079
+ );
1080
+ },
1081
+ );
1082
+ } else {
1083
+ const selectedCell = clauseOrMapper(getJoinCell, rootRowId);
1084
+ const selectedCellId = selectedOrJoinedTableId;
1085
+ if (isUndefined(selectedCell)) {
1086
+ objDel(resultRow, selectedCellId);
1087
+ } else {
1088
+ objSet(resultRow, selectedCellId, selectedCell);
1089
+ }
1090
+ }
1091
+ },
1092
+ );
1093
+ if (objIsEmpty(resultRow)) {
1094
+ selectJoinWhereStore.delRow(queryId, rootRowId);
1095
+ } else {
1096
+ selectJoinWhereStore.setRow(queryId, rootRowId, resultRow);
1097
+ }
1098
+ } else {
1099
+ mapForEach(selects, (asCellId, tableCellGetter) =>
1100
+ selectJoinWhereStore._[5](
1101
+ queryId,
1102
+ rootRowId,
1103
+ asCellId,
1104
+ tableCellGetter(getJoinCell, rootRowId),
1105
+ ),
1106
+ );
1107
+ }
1108
+ });
936
1109
  };
937
1110
  const listenToTable = (
938
1111
  rootRowId,
@@ -1051,7 +1224,7 @@ const createQueries = getCreateFunction((store) => {
1051
1224
  }),
1052
1225
  );
1053
1226
  const setQueryDefinitionImpl = (queryId, definition) => {
1054
- const stagedDefinition = [mapNew(), mapNew()];
1227
+ const stagedDefinition = [mapNew(), mapNew(), void 0, mapNew(), setNew()];
1055
1228
  let committed = false;
1056
1229
  tryCatchSync(
1057
1230
  () =>
@@ -1072,6 +1245,12 @@ const createQueries = getCreateFunction((store) => {
1072
1245
  collIsEmpty(stagedDefinition[1]) ? void 0 : stagedDefinition[1],
1073
1246
  );
1074
1247
  mapSet(preStores, queryId, stagedDefinition[2]);
1248
+ syncSelectAllListeners(queryId, stagedDefinition[3]);
1249
+ mapSet(
1250
+ referencedQueryIds,
1251
+ queryId,
1252
+ collIsEmpty(stagedDefinition[4]) ? void 0 : stagedDefinition[4],
1253
+ );
1075
1254
  committed = true;
1076
1255
  }),
1077
1256
  (error) => {
@@ -1121,6 +1300,8 @@ const createQueries = getCreateFunction((store) => {
1121
1300
  paramStore.delRow(PARAMS_TABLE, queryId);
1122
1301
  resetPreStores(queryId);
1123
1302
  resetSourceStores(queryId);
1303
+ syncSelectAllListeners(queryId);
1304
+ mapSet(referencedQueryIds, queryId);
1124
1305
  delDefinition(queryId);
1125
1306
  cleanStores();
1126
1307
  return queries;