@seedprotocol/sdk 0.1.10 → 0.1.11

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 (33) hide show
  1. package/dist/bin.js +2 -2
  2. package/dist/{index-BwUxXJ6P.js → index-CXe0BS3G.js} +2 -2
  3. package/dist/index-CXe0BS3G.js.map +1 -0
  4. package/dist/{index-C6vnbWlE.js → index-Dd2ggBQg.js} +665 -699
  5. package/dist/index-Dd2ggBQg.js.map +1 -0
  6. package/dist/main.js +1 -1
  7. package/dist/{seed-DDd7TM0Y.js → seed-CM9XY9k9.js} +3 -3
  8. package/dist/{seed-DDd7TM0Y.js.map → seed-CM9XY9k9.js.map} +1 -1
  9. package/dist/{seed-DK8XgYqz.js → seed-SjSegIMH.js} +2 -2
  10. package/dist/{seed-DK8XgYqz.js.map → seed-SjSegIMH.js.map} +1 -1
  11. package/dist/{seed-KyXHcDGt.js → seed-T0Gph_yX.js} +3 -3
  12. package/dist/{seed-KyXHcDGt.js.map → seed-T0Gph_yX.js.map} +1 -1
  13. package/dist/{seed.schema.config-D7dRgRFf.js → seed.schema.config-Dg9Q0kx4.js} +2 -2
  14. package/dist/{seed.schema.config-D7dRgRFf.js.map → seed.schema.config-Dg9Q0kx4.js.map} +1 -1
  15. package/dist/types/src/browser/db/read/getItem.d.ts.map +1 -1
  16. package/dist/types/src/browser/db/read/getItems.d.ts.map +1 -1
  17. package/dist/types/src/browser/db/read.d.ts +2 -1
  18. package/dist/types/src/browser/db/read.d.ts.map +1 -1
  19. package/dist/types/src/browser/events/item/requestAll.d.ts.map +1 -1
  20. package/dist/types/src/browser/item/class.d.ts.map +1 -1
  21. package/dist/types/src/browser/property/actors/hydrateFromDb.d.ts.map +1 -1
  22. package/dist/types/src/browser/property/actors/initialize.d.ts.map +1 -1
  23. package/dist/types/src/browser/property/actors/resolveRelatedValue.d.ts.map +1 -1
  24. package/dist/types/src/browser/property/actors/saveValueToDb.d.ts.map +1 -1
  25. package/dist/types/src/browser/property/class.d.ts.map +1 -1
  26. package/dist/types/src/browser/property/propertyMachine.d.ts.map +1 -1
  27. package/dist/types/src/browser/react/index.d.ts +1 -3
  28. package/dist/types/src/browser/react/index.d.ts.map +1 -1
  29. package/dist/types/src/types/item.d.ts +3 -3
  30. package/dist/types/src/types/item.d.ts.map +1 -1
  31. package/package.json +1 -1
  32. package/dist/index-BwUxXJ6P.js.map +0 -1
  33. package/dist/index-C6vnbWlE.js.map +0 -1
@@ -3,7 +3,7 @@ import 'reflect-metadata';
3
3
  import { Type } from '@sinclair/typebox';
4
4
  import { fromCallback, createActor, waitFor, setup, assign, emit } from 'xstate';
5
5
  import { fs, configureSingle } from '@zenfs/core';
6
- import { sql, relations, eq, isNull, and } from 'drizzle-orm';
6
+ import { sql, count, max, eq, and, or, isNull, relations } from 'drizzle-orm';
7
7
  import { drizzle } from 'drizzle-orm/sqlite-proxy';
8
8
  import debug from 'debug';
9
9
  import 'dayjs';
@@ -692,6 +692,7 @@ const initialize$3 = fromCallback(({ sendBack, input: { context } }) => {
692
692
  const { isRelation, propertyName, storageTransactionId, seedLocalId } = context;
693
693
  if (isRelation) {
694
694
  sendBack({ type: 'isRelatedProperty' });
695
+ sendBack({ type: 'initializeSuccess' });
695
696
  return;
696
697
  }
697
698
  if (!isRelation) {
@@ -814,7 +815,7 @@ const parseEasRelationPropertyName = (easPropertyName) => {
814
815
  };
815
816
  };
816
817
 
817
- sqliteTable('seeds', {
818
+ const seeds = sqliteTable('seeds', {
818
819
  localId: text('local_id').unique(),
819
820
  uid: text('uid'),
820
821
  schemaUid: text('schema_uid'),
@@ -826,7 +827,7 @@ sqliteTable('seeds', {
826
827
  _markedForDeletion: int('_marked_for_deletion'),
827
828
  });
828
829
 
829
- sqliteTable('versions', {
830
+ const versions = sqliteTable('versions', {
830
831
  localId: text('local_id').unique(),
831
832
  uid: text('uid'),
832
833
  seedLocalId: text('seed_local_id'),
@@ -839,7 +840,7 @@ sqliteTable('versions', {
839
840
  attestationRaw: text('attestation_raw'),
840
841
  });
841
842
 
842
- sqliteTable('metadata', {
843
+ const metadata = sqliteTable('metadata', {
843
844
  localId: text('local_id').unique(),
844
845
  uid: text('uid'),
845
846
  propertyName: text('property_name'),
@@ -871,38 +872,21 @@ const appState = sqliteTable('appState', {
871
872
 
872
873
  const getItemsData = (modelName) => __awaiter(void 0, void 0, void 0, function* () {
873
874
  const appDb = getAppDb();
874
- const itemsFromDbQuery = yield appDb.run(sql.raw(`SELECT s.local_id,
875
- s.uid,
876
- s.schema_uid,
877
- s.attestation_created_at,
878
- s.created_at,
879
- COUNT(v.local_id) as versions_count,
880
- MAX(v.attestation_created_at) as last_version_published_at,
881
- MAX(v.created_at) as last_local_update_at
882
- FROM seeds s
883
- JOIN versions v ON s.local_id = v.seed_local_id
884
- WHERE s.type = '${modelName.toLowerCase()}'
885
- AND (_marked_for_deletion IS NULL
886
- OR _marked_for_deletion = 0)
887
- GROUP BY s.local_id;`));
888
- if (!itemsFromDbQuery ||
889
- !itemsFromDbQuery.rows ||
890
- itemsFromDbQuery.rows.length === 0) {
891
- return [];
892
- }
893
- const itemsData = [];
894
- for (const itemDbValues of itemsFromDbQuery.rows) {
895
- itemsData.push({
896
- seedLocalId: itemDbValues[0],
897
- seedUid: itemDbValues[1],
898
- schemaUid: itemDbValues[2],
899
- attestationCreatedAt: itemDbValues[3],
900
- createdAt: itemDbValues[4],
901
- versionsCount: itemDbValues[5],
902
- lastVersionPublishedAt: itemDbValues[6],
903
- lastLocalUpdateAt: itemDbValues[7],
904
- });
905
- }
875
+ const itemsData = (yield appDb
876
+ .select({
877
+ seedLocalId: seeds.localId,
878
+ seedUid: seeds.uid,
879
+ schemaUid: seeds.schemaUid,
880
+ modelName: sql `${modelName}`,
881
+ attestationCreatedAt: seeds.attestationCreatedAt,
882
+ versionsCount: count(versions.localId),
883
+ lastVersionPublishedAt: max(versions.attestationCreatedAt),
884
+ lastLocalUpdateAt: max(versions.createdAt),
885
+ })
886
+ .from(seeds)
887
+ .leftJoin(versions, eq(seeds.localId, versions.seedLocalId))
888
+ .where(and(eq(seeds.type, modelName.toLowerCase()), or(isNull(seeds._markedForDeletion), eq(seeds._markedForDeletion, 0))))
889
+ .groupBy(seeds.localId));
906
890
  return itemsData;
907
891
  });
908
892
 
@@ -956,36 +940,32 @@ const getStorageTransactionIdForSeedUid = (seedUid) => __awaiter(void 0, void 0,
956
940
  if (seedUidToStorageTransactionId.has(seedUid)) {
957
941
  return seedUidToStorageTransactionId.get(seedUid);
958
942
  }
959
- const storageTransactionIdStatement = `SELECT property_value,
960
- MAX(attestation_created_at),
961
- ref_resolved_display_value,
962
- ref_resolved_value,
963
- ref_seed_type,
964
- eas_data_type
965
- FROM metadata
966
- WHERE (
967
- seed_uid = '${seedUid}'
968
- AND property_name = 'storageTransactionId'
969
- );
970
- `;
971
- const { rows } = yield runQueryForStatement(storageTransactionIdStatement);
972
- if (!rows || rows.length === 0 || !rows[0][0]) {
943
+ const appDb = getAppDb();
944
+ const results = (yield appDb
945
+ .select({
946
+ storageTransactionId: metadata.propertyValue,
947
+ })
948
+ .from(metadata)
949
+ .where(and(eq(metadata.seedUid, seedUid), eq(metadata.propertyName, 'storageTransactionId'))));
950
+ if (!results || results.length === 0) {
973
951
  return;
974
952
  }
975
- seedUidToStorageTransactionId.set(seedUid, rows[0][0]);
976
- return rows[0][0];
953
+ seedUidToStorageTransactionId.set(seedUid, results[0].storageTransactionId);
954
+ return results[0].storageTransactionId;
977
955
  });
978
956
  const getRelationValueData = (propertyValue) => __awaiter(void 0, void 0, void 0, function* () {
979
- const propertyValueStatement = `SELECT property_value,
980
- MAX(attestation_created_at),
981
- ref_resolved_display_value,
982
- ref_resolved_value,
983
- ref_seed_type,
984
- eas_data_type
985
- FROM metadata
986
- WHERE property_value = '${propertyValue}';
987
- `;
988
- const { rows } = yield runQueryForStatement(propertyValueStatement);
957
+ const appDb = getAppDb();
958
+ const rows = (yield appDb
959
+ .select({
960
+ propertyValue: metadata.propertyValue,
961
+ attestationCreatedAt: max(metadata.attestationCreatedAt),
962
+ refResolvedDisplayValue: metadata.refResolvedDisplayValue,
963
+ refResolvedValue: metadata.refResolvedValue,
964
+ refSeedType: metadata.refSeedType,
965
+ easDataType: metadata.easDataType,
966
+ })
967
+ .from(metadata)
968
+ .where(eq(metadata.propertyValue, propertyValue)));
989
969
  if (!rows || rows.length === 0) {
990
970
  return;
991
971
  }
@@ -1055,6 +1035,10 @@ const resolveRelatedValue = fromCallback(({ sendBack, input: { context } }) => {
1055
1035
  });
1056
1036
  return true;
1057
1037
  }
1038
+ if (Array.isArray(propertyValue)) {
1039
+ // TODO: Handle array of seedUids
1040
+ return;
1041
+ }
1058
1042
  const storageTransactionId = yield getStorageTransactionIdForSeedUid(propertyValue);
1059
1043
  if (storageTransactionId) {
1060
1044
  if (storageTransactionIdToContentUrl.has(storageTransactionId)) {
@@ -1087,10 +1071,8 @@ const resolveRelatedValue = fromCallback(({ sendBack, input: { context } }) => {
1087
1071
  }
1088
1072
  const relationValueData = yield getRelationValueData(propertyValue);
1089
1073
  if (relationValueData) {
1090
- const propertyValueFromDb = relationValueData[0];
1091
- const refResolvedValue = relationValueData[3];
1092
- relationValueData[4];
1093
- relationValueData[5];
1074
+ const { refResolvedValue } = relationValueData;
1075
+ const propertyValueFromDb = relationValueData.propertyValue;
1094
1076
  // This handles a local-only relation value and resolves from the filesystem
1095
1077
  if (refResolvedValue &&
1096
1078
  propertyRecordSchema.dataType === 'Relation' &&
@@ -1158,12 +1140,15 @@ const resolveRelatedValue = fromCallback(({ sendBack, input: { context } }) => {
1158
1140
  }
1159
1141
  });
1160
1142
  _resolveRelatedValue().then((success) => {
1161
- if (!success) {
1162
- sendBack({
1163
- type: 'resolvingRelatedValueDone',
1164
- });
1165
- }
1166
- return;
1143
+ // if (success) {
1144
+ // sendBack({
1145
+ // type: 'resolvingRelatedValueDone',
1146
+ // })
1147
+ // }
1148
+ // return
1149
+ sendBack({
1150
+ type: 'resolvingRelatedValueDone',
1151
+ });
1167
1152
  });
1168
1153
  });
1169
1154
  // const eventKey = `storage.transaction.${initialValue}.contentUrl.response`
@@ -1586,164 +1571,6 @@ const getAddressesFromDb = () => __awaiter(void 0, void 0, void 0, function* ()
1586
1571
  return JSON.parse(addressArrayString);
1587
1572
  });
1588
1573
 
1589
- const logger$c = debug('app:property:actors:hydrateFromDb');
1590
- const hydrateFromDb = fromCallback(({ sendBack, input: { context } }) => {
1591
- const { seedUid, seedLocalId, propertyName: propertyNameRaw, propertyValue, propertyRecordSchema, itemModelName, } = context;
1592
- let propertyName = propertyNameRaw;
1593
- if (propertyRecordSchema &&
1594
- propertyRecordSchema.ref &&
1595
- propertyRecordSchema.dataType === 'Relation' &&
1596
- !propertyNameRaw.endsWith('Id')) {
1597
- propertyName = propertyNameRaw + 'Id';
1598
- }
1599
- if (propertyRecordSchema &&
1600
- propertyRecordSchema.ref &&
1601
- propertyRecordSchema.dataType === 'List' &&
1602
- !propertyNameRaw.endsWith('Ids')) {
1603
- propertyName = propertyNameRaw + 'Ids';
1604
- }
1605
- const _hydrateFromDb = () => __awaiter(void 0, void 0, void 0, function* () {
1606
- const db = getAppDb();
1607
- let hydrateQuery;
1608
- let safeValue = propertyValue;
1609
- let propertyNameQueryString = `property_name = '${propertyName}'`;
1610
- if (safeValue && typeof propertyValue === 'string') {
1611
- safeValue = escapeSqliteString(propertyValue);
1612
- }
1613
- if (propertyRecordSchema &&
1614
- propertyRecordSchema.ref &&
1615
- propertyRecordSchema.dataType === 'Relation') {
1616
- let missingPropertyNameVariant;
1617
- if (propertyName.endsWith('Id')) {
1618
- missingPropertyNameVariant = propertyName.slice(0, -2);
1619
- }
1620
- if (!propertyName.endsWith('Id')) {
1621
- missingPropertyNameVariant = propertyName + 'Id';
1622
- }
1623
- propertyNameQueryString += ` OR property_name = '${missingPropertyNameVariant}'`;
1624
- }
1625
- if (seedUid && !seedLocalId) {
1626
- hydrateQuery = yield db.run(sql.raw(`SELECT local_id,
1627
- uid,
1628
- property_name,
1629
- property_value,
1630
- seed_local_id,
1631
- seed_uid,
1632
- schema_uid,
1633
- ref_resolved_value,
1634
- ref_resolved_display_value
1635
- FROM metadata
1636
- WHERE seed_uid = '${seedUid}'
1637
- AND (${propertyNameQueryString})
1638
- ORDER BY COALESCE(attestation_created_at, created_at) DESC;
1639
- `));
1640
- }
1641
- if (seedUid && seedLocalId) {
1642
- hydrateQuery = yield db.run(sql.raw(`SELECT local_id,
1643
- uid,
1644
- property_name,
1645
- property_value,
1646
- seed_local_id,
1647
- seed_uid,
1648
- schema_uid,
1649
- ref_resolved_value,
1650
- ref_resolved_display_value
1651
- FROM metadata
1652
- WHERE seed_local_id = '${seedLocalId}'
1653
- AND (${propertyNameQueryString})
1654
- AND seed_uid = '${seedUid}'
1655
- ORDER BY COALESCE(attestation_created_at, created_at) DESC;
1656
- `));
1657
- }
1658
- if (!seedUid && seedLocalId) {
1659
- hydrateQuery = yield db.run(sql.raw(`SELECT local_id,
1660
- uid,
1661
- property_name,
1662
- property_value,
1663
- seed_local_id,
1664
- seed_uid,
1665
- schema_uid,
1666
- ref_resolved_value,
1667
- ref_resolved_display_value
1668
- FROM metadata
1669
- WHERE seed_local_id = '${seedLocalId}'
1670
- AND (${propertyNameQueryString})
1671
- ORDER BY COALESCE(attestation_created_at, created_at) DESC;
1672
- `));
1673
- }
1674
- if (hydrateQuery && hydrateQuery.rows && hydrateQuery.rows.length > 0) {
1675
- const firstRow = hydrateQuery.rows[0];
1676
- const localId = firstRow[0];
1677
- const uid = firstRow[1];
1678
- const propertyNameFromDb = firstRow[2];
1679
- const propertyValueFromDb = firstRow[3];
1680
- const seedLocalIdFromDb = firstRow[4];
1681
- const seedUidFromDb = firstRow[5];
1682
- const schemaUidFromDb = firstRow[6];
1683
- const refResolvedValue = firstRow[7];
1684
- const refResolvedDisplayValue = firstRow[8];
1685
- if (propertyNameFromDb !== propertyName) {
1686
- logger$c(`Property name from db ${propertyNameFromDb} does not match property name ${propertyName} for Property.${localId}`);
1687
- }
1688
- if (propertyValueFromDb !== propertyValue) {
1689
- logger$c(`Property value from db ${propertyValueFromDb} does not match property value ${propertyValue} for Property.${localId}`);
1690
- }
1691
- if (seedLocalIdFromDb !== seedLocalId) {
1692
- logger$c(`Seed local id from db ${seedLocalIdFromDb} does not match seed local id ${seedLocalId} for Property.${localId}`);
1693
- }
1694
- if (seedUidFromDb !== seedUid) {
1695
- logger$c(`Seed uid from db ${seedUidFromDb} does not match seed uid ${seedUid} for Property.${localId}`);
1696
- }
1697
- sendBack({
1698
- type: 'updateContext',
1699
- localId,
1700
- uid,
1701
- propertyName: propertyNameFromDb,
1702
- propertyValue: propertyValueFromDb,
1703
- seedLocalId: seedLocalIdFromDb,
1704
- seedUid: seedUidFromDb,
1705
- schemaUid: schemaUidFromDb,
1706
- resolveValue: refResolvedValue,
1707
- resolveDisplayValue: refResolvedDisplayValue,
1708
- renderValue: refResolvedDisplayValue,
1709
- });
1710
- if (propertyNameFromDb === 'storageTransactionId') {
1711
- const { Item } = yield import('./index-BwUxXJ6P.js');
1712
- const item = yield Item.find({
1713
- seedLocalId,
1714
- modelName: itemModelName,
1715
- });
1716
- if (item) {
1717
- for (const [propertyName, property] of Object.entries(item.properties)) {
1718
- if (propertyName === 'html' &&
1719
- propertyValueFromDb &&
1720
- propertyValueFromDb.length === 43) {
1721
- const htmlFilePath = `/files/html/${propertyValueFromDb}.html`;
1722
- const exists = yield fs.promises.exists(htmlFilePath);
1723
- if (!exists) {
1724
- logger$c(`HTML file does not exist for Property.${localId} at ${htmlFilePath}`);
1725
- return;
1726
- }
1727
- const renderValue = yield fs.promises
1728
- .readFile(htmlFilePath, 'utf8')
1729
- .catch((error) => {
1730
- logger$c('Error reading html file', error);
1731
- });
1732
- property
1733
- .getService()
1734
- .send({ type: 'updateRenderValue', renderValue });
1735
- return;
1736
- }
1737
- }
1738
- }
1739
- }
1740
- }
1741
- });
1742
- _hydrateFromDb().then(() => {
1743
- sendBack({ type: 'hydrateFromDbSuccess' });
1744
- });
1745
- });
1746
-
1747
1574
  const eventEmitter = new EventEmitter();
1748
1575
 
1749
1576
  const APP_DB_CONFIG = 'browser.app.db.config.ts';
@@ -1790,7 +1617,7 @@ const internalPropertyNames = [
1790
1617
  ];
1791
1618
 
1792
1619
  var _a$2;
1793
- const logger$b = debug('app:property:class');
1620
+ const logger$c = debug('app:property:class');
1794
1621
  const namesThatEndWithId = [];
1795
1622
  class ItemProperty {
1796
1623
  // private constructor(localIdOrUid) {
@@ -1838,7 +1665,7 @@ class ItemProperty {
1838
1665
  serviceInput.propertyValue = JSON.parse(propertyValue);
1839
1666
  }
1840
1667
  catch (e) {
1841
- logger$b('List property value is not JSON', e);
1668
+ logger$c('List property value is not JSON', e);
1842
1669
  }
1843
1670
  }
1844
1671
  const propertyNameSingular = pluralize(propertyName, 1);
@@ -1900,42 +1727,42 @@ class ItemProperty {
1900
1727
  this._service.start();
1901
1728
  }
1902
1729
  _updateResponseListener(event) {
1903
- logger$b(`[ItemProperty] [_updateResponseListener] [${this.itemModelName}.${this.seedLocalId}] ${this.propertyName} event`, event);
1730
+ logger$c(`[ItemProperty] [_updateResponseListener] [${this.itemModelName}.${this.seedLocalId}] ${this.propertyName} event`, event);
1904
1731
  }
1905
1732
  static create(props) {
1906
1733
  const { propertyName, seedLocalId, uid } = props;
1907
1734
  if (seedLocalId && propertyName) {
1908
1735
  const cacheKey = ItemProperty.cacheKey(seedLocalId, propertyName);
1909
- if (this.instanceCache.has(cacheKey)) {
1910
- const { instance, refCount } = this.instanceCache.get(cacheKey);
1911
- this.instanceCache.set(cacheKey, {
1736
+ if (ItemProperty.instanceCache.has(cacheKey)) {
1737
+ const { instance, refCount } = ItemProperty.instanceCache.get(cacheKey);
1738
+ ItemProperty.instanceCache.set(cacheKey, {
1912
1739
  instance,
1913
1740
  refCount: refCount + 1,
1914
1741
  });
1915
- if (instance.status === 'idle') {
1916
- instance.getService().send({ type: 'refresh' });
1917
- }
1918
- if (seedLocalId === 'R4RYj2pYIQ' && propertyName === 'html') {
1919
- logger$b('[property/class] [create] [R4RYj2pYIQ] returning cached instance', instance.getService().getSnapshot().context);
1920
- }
1921
1742
  return instance;
1922
1743
  }
1744
+ if (!ItemProperty.instanceCache.has(cacheKey)) {
1745
+ const newInstance = new ItemProperty(props);
1746
+ ItemProperty.instanceCache.set(cacheKey, {
1747
+ instance: newInstance,
1748
+ refCount: 1,
1749
+ });
1750
+ return newInstance;
1751
+ }
1923
1752
  }
1924
1753
  if (uid) {
1925
1754
  if (this.instanceCache.has(uid)) {
1926
1755
  const { instance, refCount } = this.instanceCache.get(uid);
1927
1756
  this.instanceCache.set(uid, { instance, refCount: refCount + 1 });
1928
- if (seedLocalId === 'R4RYj2pYIQ' && propertyName === 'html') {
1929
- logger$b('[property/class] [create] [uid] [R4RYj2pYIQ] returning cached instance', instance.getService().getSnapshot().context);
1930
- }
1931
1757
  return instance;
1932
1758
  }
1759
+ if (!this.instanceCache.has(uid)) {
1760
+ const newInstance = new ItemProperty(props);
1761
+ this.instanceCache.set(uid, { instance: newInstance, refCount: 1 });
1762
+ return newInstance;
1763
+ }
1933
1764
  }
1934
- const newInstance = new ItemProperty(props);
1935
- if (props.seedLocalId === 'R4RYj2pYIQ' && propertyName === 'html') {
1936
- logger$b('[property/class] [create] [R4RYj2pYIQ] returning new instance', props, newInstance.getService().getSnapshot().context);
1937
- }
1938
- return newInstance;
1765
+ return new ItemProperty(props);
1939
1766
  }
1940
1767
  static find(_b) {
1941
1768
  return __awaiter(this, arguments, void 0, function* ({ propertyName, seedLocalId, }) {
@@ -2036,7 +1863,7 @@ class ItemProperty {
2036
1863
  }
2037
1864
  unload() {
2038
1865
  this._service.stop();
2039
- logger$b(`[XXXXXX] [ItemProperty] [${this.seedLocalId}] [unload] removing listener`, this._updateResponseEvent);
1866
+ logger$c(`[XXXXXX] [ItemProperty] [${this.seedLocalId}] [unload] removing listener`, this._updateResponseEvent);
2040
1867
  eventEmitter.removeListener(this._updateResponseEvent, this._updateResponseListener);
2041
1868
  }
2042
1869
  }
@@ -2130,7 +1957,7 @@ const getContentUrlFromPath = (path) => __awaiter(void 0, void 0, void 0, functi
2130
1957
  return URL.createObjectURL(fileHandler);
2131
1958
  });
2132
1959
 
2133
- const logger$a = debug('app:global:actors');
1960
+ const logger$b = debug('app:global:actors');
2134
1961
  const initialize$1 = fromCallback(({ sendBack, input: { event, context } }) => {
2135
1962
  const { internalService, models, endpoints } = context;
2136
1963
  const { addresses } = event;
@@ -2151,7 +1978,7 @@ const initialize$1 = fromCallback(({ sendBack, input: { event, context } }) => {
2151
1978
  const _initInternal = () => __awaiter(void 0, void 0, void 0, function* () {
2152
1979
  return new Promise((resolve) => {
2153
1980
  internalSubscription = internalService.subscribe((snapshot) => {
2154
- logger$a('[sdk] [internal] snapshot', snapshot);
1981
+ logger$b('[sdk] [internal] snapshot', snapshot);
2155
1982
  if (snapshot.value === 'ready') {
2156
1983
  resolve();
2157
1984
  }
@@ -2160,10 +1987,10 @@ const initialize$1 = fromCallback(({ sendBack, input: { event, context } }) => {
2160
1987
  });
2161
1988
  });
2162
1989
  _initFileSystem().then(() => {
2163
- logger$a('[global/actors] File system initialized');
1990
+ logger$b('[global/actors] File system initialized');
2164
1991
  });
2165
1992
  _initInternal().then(() => {
2166
- logger$a('[global/actors] Internal initialized');
1993
+ logger$b('[global/actors] Internal initialized');
2167
1994
  sendBack({ type: GLOBAL_INITIALIZING_INTERNAL_SERVICE_READY });
2168
1995
  internalSubscription === null || internalSubscription === void 0 ? void 0 : internalSubscription.unsubscribe();
2169
1996
  });
@@ -2184,12 +2011,12 @@ const addModelsToDb = fromCallback(({ sendBack, input: { context } }) => {
2184
2011
  if (!models$1) {
2185
2012
  return;
2186
2013
  }
2187
- const { models: SeedModels } = yield import('./seed.schema.config-D7dRgRFf.js');
2014
+ const { models: SeedModels } = yield import('./seed.schema.config-Dg9Q0kx4.js');
2188
2015
  const allModels = Object.assign(Object.assign({}, SeedModels), models$1);
2189
2016
  let hasModelsInDb = false;
2190
2017
  const schemaDefsByModelName = new Map();
2191
2018
  for (const [modelName, _] of Object.entries(allModels)) {
2192
- logger$a('[helpers/db] [addModelsToInternalDb] starting modelName:', modelName);
2019
+ logger$b('[helpers/db] [addModelsToInternalDb] starting modelName:', modelName);
2193
2020
  let foundModel;
2194
2021
  const foundModelsQuery = yield sdkConfigDb
2195
2022
  .select()
@@ -2199,7 +2026,7 @@ const addModelsToDb = fromCallback(({ sendBack, input: { context } }) => {
2199
2026
  yield sdkConfigDb.insert(models).values({
2200
2027
  name: modelName,
2201
2028
  });
2202
- logger$a('[global/actors] [addModelsToDb] inserted model:', modelName);
2029
+ logger$b('[global/actors] [addModelsToDb] inserted model:', modelName);
2203
2030
  const foundModels = yield sdkConfigDb
2204
2031
  .select({
2205
2032
  id: models.id,
@@ -2283,7 +2110,7 @@ const getSchemaForModel = fromCallback(({ sendBack, input: { context, event } })
2283
2110
  if (!model) {
2284
2111
  throw new Error(`Model ${modelName} not found`);
2285
2112
  }
2286
- logger$a('[service/actor] [getSchemaForModel] model:', model);
2113
+ logger$b('[service/actor] [getSchemaForModel] model:', model);
2287
2114
  sendBack({ type: 'schemaForModel', schema: model.schema });
2288
2115
  return () => { };
2289
2116
  });
@@ -2337,7 +2164,7 @@ class SqliteConnectionManager {
2337
2164
  }
2338
2165
  }
2339
2166
 
2340
- const logger$9 = debug('app:services:internal:helpers');
2167
+ const logger$a = debug('app:services:internal:helpers');
2341
2168
  /**
2342
2169
  * Recursively create directories if they don't exist.
2343
2170
  * @param {string} dirPath - The directory path to create.
@@ -2413,7 +2240,7 @@ const downloadFile = (url, localFilePath) => __awaiter(void 0, void 0, void 0, f
2413
2240
  if (JSON.stringify(error).includes('File exists')) {
2414
2241
  yield fs.promises.readFile(localFilePath, 'utf-8');
2415
2242
  }
2416
- logger$9(`[Error] Failed to download file from ${url}:`, error);
2243
+ logger$a(`[Error] Failed to download file from ${url}:`, error);
2417
2244
  }
2418
2245
  busy = false;
2419
2246
  });
@@ -2451,7 +2278,7 @@ const syncDbFiles = (_a) => __awaiter(void 0, [_a], void 0, function* ({ filePat
2451
2278
  const fileList = yield fetchDirectory(filePaths);
2452
2279
  yield fetchFilesRecursively(files, BROWSER_FS_TOP_DIR, fileList);
2453
2280
  yield confirmFilesExist(fileList);
2454
- logger$9('[syncDbFiles] Files synced!');
2281
+ logger$a('[syncDbFiles] Files synced!');
2455
2282
  });
2456
2283
 
2457
2284
  const uploadBinaryData = fromCallback(({ sendBack, receive, input }) => { });
@@ -2761,7 +2588,7 @@ const getArweave = () => {
2761
2588
  });
2762
2589
  };
2763
2590
 
2764
- const logger$8 = debug('app:files:download');
2591
+ const logger$9 = debug('app:files:download');
2765
2592
  const downloadAllFilesRequestHandler = (_a) => __awaiter(void 0, [_a], void 0, function* ({ endpoints, eventId, }) {
2766
2593
  yield syncDbFiles(endpoints);
2767
2594
  eventEmitter.emit('fs.downloadAll.success', { eventId });
@@ -2831,7 +2658,7 @@ const downloadAllFilesBinaryRequestHandler = () => __awaiter(void 0, void 0, voi
2831
2658
  try {
2832
2659
  const res = yield fetch(`https://${ARWEAVE_HOST}/tx/${transactionId}/status`);
2833
2660
  if (res.status !== 200) {
2834
- logger$8(`[fetchAll/actors] [fetchAllBinaryData] error fetching transaction data for ${transactionId}`);
2661
+ logger$9(`[fetchAll/actors] [fetchAllBinaryData] error fetching transaction data for ${transactionId}`);
2835
2662
  excludedTransactions.add(transactionId);
2836
2663
  yield writeAppState(seedDb, 'excludedTransactions', JSON.stringify(Array.from(excludedTransactions)));
2837
2664
  continue;
@@ -2845,7 +2672,7 @@ const downloadAllFilesBinaryRequestHandler = () => __awaiter(void 0, void 0, voi
2845
2672
  console.error(`[fetchAll/actors] [fetchAllBinaryData] error fetching transaction data for ${transactionId}`, error);
2846
2673
  });
2847
2674
  if (!dataString) {
2848
- logger$8(`[fetchAll/actors] [fetchAllBinaryData] transaction ${transactionId} data not found`);
2675
+ logger$9(`[fetchAll/actors] [fetchAllBinaryData] transaction ${transactionId} data not found`);
2849
2676
  }
2850
2677
  let contentType = identifyString(dataString);
2851
2678
  if (contentType !== 'json' &&
@@ -2853,7 +2680,7 @@ const downloadAllFilesBinaryRequestHandler = () => __awaiter(void 0, void 0, voi
2853
2680
  contentType !== 'html') {
2854
2681
  const possibleImageType = getImageDataType(dataString);
2855
2682
  if (!possibleImageType) {
2856
- logger$8(`[fetchAll/actors] [fetchAllBinaryData] transaction ${transactionId} data not in expected format: ${possibleImageType}`);
2683
+ logger$9(`[fetchAll/actors] [fetchAllBinaryData] transaction ${transactionId} data not in expected format: ${possibleImageType}`);
2857
2684
  continue;
2858
2685
  }
2859
2686
  contentType = possibleImageType;
@@ -2916,7 +2743,7 @@ const downloadAllFilesBinaryRequestHandler = () => __awaiter(void 0, void 0, voi
2916
2743
  }
2917
2744
  }
2918
2745
  catch (error) {
2919
- logger$8(error);
2746
+ logger$9(error);
2920
2747
  }
2921
2748
  }
2922
2749
  });
@@ -2962,7 +2789,7 @@ const isFsInitialized = () => {
2962
2789
  return isInitialized;
2963
2790
  };
2964
2791
 
2965
- const logger$7 = debug('app:internal:actors');
2792
+ const logger$8 = debug('app:internal:actors');
2966
2793
  let sqliteWasmClient;
2967
2794
  let manager;
2968
2795
  const validateInput = fromCallback(({ sendBack, input: { event } }) => {
@@ -3015,12 +2842,12 @@ const prepareDb = fromCallback(({ sendBack, input: { event, context } }) => {
3015
2842
  });
3016
2843
  const configureFs = fromCallback(({ sendBack, input: { context } }) => {
3017
2844
  const { endpoints, seedDbService, appDbService, sdkDbService } = context;
3018
- logger$7('[internal/actors] [configureFs] Configuring FS');
2845
+ logger$8('[internal/actors] [configureFs] Configuring FS');
3019
2846
  const services = [seedDbService, appDbService, sdkDbService];
3020
2847
  const _configureFs = () => __awaiter(void 0, void 0, void 0, function* () {
3021
- logger$7('[internal/actors] [configureFs] calling _configureFs');
3022
- logger$7('[internal/actors] [configureFs] areFsListenersReady:', areFsListenersReady());
3023
- logger$7('[internal/actors] [configureFs] isFsInitialized:', isFsInitialized());
2848
+ logger$8('[internal/actors] [configureFs] calling _configureFs');
2849
+ logger$8('[internal/actors] [configureFs] areFsListenersReady:', areFsListenersReady());
2850
+ logger$8('[internal/actors] [configureFs] isFsInitialized:', isFsInitialized());
3024
2851
  yield waitForEvent({
3025
2852
  req: {
3026
2853
  eventLabel: 'fs.downloadAll.request',
@@ -3052,7 +2879,7 @@ const configureFs = fromCallback(({ sendBack, input: { context } }) => {
3052
2879
  // }, 200)
3053
2880
  // })
3054
2881
  })));
3055
- logger$7('[internal/actors] [configureFs] fs configured!');
2882
+ logger$8('[internal/actors] [configureFs] fs configured!');
3056
2883
  });
3057
2884
  // Some of our dependencies use fs sync functions, which don't work with
3058
2885
  // OPFS. ZenFS creates an async cache of all files so that the sync functions
@@ -3138,14 +2965,14 @@ const saveConfig = fromCallback(({ sendBack, receive, input: { context } }) => {
3138
2965
  },
3139
2966
  setWhere: sql `key = 'addresses'`,
3140
2967
  });
3141
- logger$7('[sdk] [internal/actors] Should be done saving');
2968
+ logger$8('[sdk] [internal/actors] Should be done saving');
3142
2969
  }
3143
2970
  catch (error) {
3144
2971
  console.error('Error saving config:', error);
3145
2972
  }
3146
2973
  });
3147
2974
  _saveConfig().then(() => {
3148
- logger$7('[sdk] [internal/actors] Successfully saved config');
2975
+ logger$8('[sdk] [internal/actors] Successfully saved config');
3149
2976
  return sendBack({ type: INTERNAL_SAVING_CONFIG_SUCCESS });
3150
2977
  });
3151
2978
  return () => { };
@@ -3170,7 +2997,7 @@ const loadAppDb = fromCallback(({ sendBack, input: { context } }) => {
3170
2997
  });
3171
2998
  _loadAppDb().then(() => {
3172
2999
  sendBack({ type: INTERNAL_LOADING_APP_DB_SUCCESS });
3173
- logger$7('[sdk] [internal/actors] Successfully loaded app DB');
3000
+ logger$8('[sdk] [internal/actors] Successfully loaded app DB');
3174
3001
  });
3175
3002
  return () => {
3176
3003
  if (subscription) {
@@ -3180,7 +3007,7 @@ const loadAppDb = fromCallback(({ sendBack, input: { context } }) => {
3180
3007
  });
3181
3008
  const loadSdkDb = fromCallback(({ sendBack, input: { context } }) => {
3182
3009
  const { sdkDbService } = context;
3183
- logger$7('[sdk] [internal/actors] Loading SDK DB');
3010
+ logger$8('[sdk] [internal/actors] Loading SDK DB');
3184
3011
  let subscription;
3185
3012
  const _loadSdkDb = () => __awaiter(void 0, void 0, void 0, function* () {
3186
3013
  return new Promise((resolve) => {
@@ -3203,7 +3030,7 @@ const loadSdkDb = fromCallback(({ sendBack, input: { context } }) => {
3203
3030
  });
3204
3031
  _loadSdkDb().then(() => {
3205
3032
  sendBack({ type: INTERNAL_LOADING_SDK_DB_SUCCESS });
3206
- logger$7('[sdk] [internal/actors] Successfully loaded SDK DB');
3033
+ logger$8('[sdk] [internal/actors] Successfully loaded SDK DB');
3207
3034
  });
3208
3035
  return () => {
3209
3036
  if (subscription) {
@@ -3212,7 +3039,7 @@ const loadSdkDb = fromCallback(({ sendBack, input: { context } }) => {
3212
3039
  };
3213
3040
  });
3214
3041
 
3215
- const logger$6 = debug('app:services:db:machine');
3042
+ const logger$7 = debug('app:services:db:machine');
3216
3043
  const { CHECKING_STATUS, VALIDATING, WAITING_FOR_FILES, CONNECTING_TO_DB, MIGRATING, } = DbState;
3217
3044
  const dbMachine = setup({
3218
3045
  types: {
@@ -3233,7 +3060,7 @@ const dbMachine = setup({
3233
3060
  [DB_WAITING_FOR_FILES_RECEIVED]: {
3234
3061
  actions: assign({
3235
3062
  hasFiles: ({ event }) => {
3236
- logger$6('[db/machine] DB_WAITING_FOR_FILES_RECEIVED event:', event);
3063
+ logger$7('[db/machine] DB_WAITING_FOR_FILES_RECEIVED event:', event);
3237
3064
  return true;
3238
3065
  },
3239
3066
  }),
@@ -3242,8 +3069,8 @@ const dbMachine = setup({
3242
3069
  target: `.${CHECKING_STATUS}`,
3243
3070
  actions: assign({
3244
3071
  hasFiles: ({ context, event }) => {
3245
- logger$6('[db/machine] updateHasFiles event:', event);
3246
- logger$6('[db/machine] updateHasFiles context:', context);
3072
+ logger$7('[db/machine] updateHasFiles event:', event);
3073
+ logger$7('[db/machine] updateHasFiles context:', context);
3247
3074
  return event.hasFiles;
3248
3075
  },
3249
3076
  }),
@@ -3364,7 +3191,7 @@ const dbMachine = setup({
3364
3191
  },
3365
3192
  });
3366
3193
 
3367
- const logger$5 = debug('app:services:internal:machine');
3194
+ const logger$6 = debug('app:services:internal:machine');
3368
3195
  createBrowserInspector({
3369
3196
  autoStart: false,
3370
3197
  });
@@ -3526,7 +3353,7 @@ const internalMachine = setup({
3526
3353
  [INTERNAL_LOADING_APP_DB_SUCCESS]: {
3527
3354
  target: 'appDbLoaded',
3528
3355
  actions: () => {
3529
- logger$5('[sdk] [internal/index] App DB loaded!');
3356
+ logger$6('[sdk] [internal/index] App DB loaded!');
3530
3357
  },
3531
3358
  },
3532
3359
  },
@@ -3538,7 +3365,7 @@ const internalMachine = setup({
3538
3365
  appDbLoaded: {
3539
3366
  type: 'final',
3540
3367
  entry: () => {
3541
- logger$5('[sdk] [internal/index] Entered appDbLoaded!');
3368
+ logger$6('[sdk] [internal/index] Entered appDbLoaded!');
3542
3369
  },
3543
3370
  },
3544
3371
  },
@@ -3551,7 +3378,7 @@ const internalMachine = setup({
3551
3378
  [INTERNAL_LOADING_SDK_DB_SUCCESS]: {
3552
3379
  target: 'sdkConfigDbLoaded',
3553
3380
  actions: () => {
3554
- logger$5('[sdk] [internal/index] SDK Config DB loaded!');
3381
+ logger$6('[sdk] [internal/index] SDK Config DB loaded!');
3555
3382
  },
3556
3383
  },
3557
3384
  },
@@ -3563,7 +3390,7 @@ const internalMachine = setup({
3563
3390
  sdkConfigDbLoaded: {
3564
3391
  type: 'final',
3565
3392
  entry: () => {
3566
- logger$5('[sdk] [internal/index] Entered sdkConfigDbLoaded!');
3393
+ logger$6('[sdk] [internal/index] Entered sdkConfigDbLoaded!');
3567
3394
  },
3568
3395
  },
3569
3396
  },
@@ -3572,7 +3399,7 @@ const internalMachine = setup({
3572
3399
  onDone: {
3573
3400
  target: 'ready',
3574
3401
  actions: () => {
3575
- logger$5('[sdk] [internal/index] All DBs loaded! Should be headed to ready');
3402
+ logger$6('[sdk] [internal/index] All DBs loaded! Should be headed to ready');
3576
3403
  eventEmitter.emit('allDbsLoaded');
3577
3404
  },
3578
3405
  },
@@ -3584,7 +3411,7 @@ const internalMachine = setup({
3584
3411
  },
3585
3412
  ready: {
3586
3413
  entry: () => {
3587
- logger$5('[sdk] [internal/index] Ready!');
3414
+ logger$6('[sdk] [internal/index] Ready!');
3588
3415
  },
3589
3416
  meta: {
3590
3417
  displayText: "Crossing the t's ...",
@@ -3599,7 +3426,7 @@ const internalMachine = setup({
3599
3426
  },
3600
3427
  },
3601
3428
  entry: () => {
3602
- logger$5('[sdk] [internal/index] Error!');
3429
+ logger$6('[sdk] [internal/index] Error!');
3603
3430
  },
3604
3431
  meta: {
3605
3432
  displayText: 'Whoops! Something went wrong.',
@@ -3806,7 +3633,7 @@ const fetchDbData = fromCallback(({ sendBack, input: { context } }) => {
3806
3633
  return () => { };
3807
3634
  });
3808
3635
 
3809
- const logger$4 = debug('app:allItemsActors:fetchSeeds');
3636
+ const logger$5 = debug('app:allItemsActors:fetchSeeds');
3810
3637
  const fetchSeeds = fromCallback(({ sendBack, input: { context } }) => {
3811
3638
  const { queryVariables, modelName } = context;
3812
3639
  if (!queryVariables) {
@@ -3816,7 +3643,7 @@ const fetchSeeds = fromCallback(({ sendBack, input: { context } }) => {
3816
3643
  const _fetchSeeds = () => __awaiter(void 0, void 0, void 0, function* () {
3817
3644
  const queryKey = [`getSeeds${modelName}`];
3818
3645
  const cachedResults = queryClient.getQueryData(queryKey);
3819
- logger$4(`[allItemsActors] [fetchSeeds] cachedResults ${Date.now()}`, cachedResults);
3646
+ logger$5(`[allItemsActors] [fetchSeeds] cachedResults ${Date.now()}`, cachedResults);
3820
3647
  const results = yield queryClient.fetchQuery({
3821
3648
  queryKey,
3822
3649
  queryFn: () => __awaiter(void 0, void 0, void 0, function* () { return easClient.request(GET_SEEDS, queryVariables); }),
@@ -4304,11 +4131,11 @@ const globalMachine = setup({
4304
4131
  (_a) => __awaiter(void 0, [_a], void 0, function* ({ context }) {
4305
4132
  let SeedClass;
4306
4133
  if (context.environment === 'node') {
4307
- const { SeedNode } = yield import('./seed-KyXHcDGt.js');
4134
+ const { SeedNode } = yield import('./seed-T0Gph_yX.js');
4308
4135
  SeedClass = SeedNode;
4309
4136
  }
4310
4137
  else {
4311
- const { SeedBrowser } = yield import('./seed-DDd7TM0Y.js');
4138
+ const { SeedBrowser } = yield import('./seed-CM9XY9k9.js');
4312
4139
  SeedClass = SeedBrowser;
4313
4140
  }
4314
4141
  return SeedClass;
@@ -5399,7 +5226,7 @@ const getSeedData = (_a) => __awaiter(void 0, [_a], void 0, function* ({ seedLoc
5399
5226
  };
5400
5227
  });
5401
5228
 
5402
- const logger$3 = debug('app:db:queries:getItem');
5229
+ const logger$4 = debug('app:db:queries:getItem');
5403
5230
  const getItemDataFromDb = (_a) => __awaiter(void 0, [_a], void 0, function* ({ modelName, seedLocalId, seedUid, }) {
5404
5231
  if (!seedLocalId && !seedUid) {
5405
5232
  throw new Error('[db/queries] [getItem] no seedLocalId or seedUid');
@@ -5407,7 +5234,7 @@ const getItemDataFromDb = (_a) => __awaiter(void 0, [_a], void 0, function* ({ m
5407
5234
  if (seedUid && !seedLocalId) {
5408
5235
  const seedData = yield getSeedData({ seedUid });
5409
5236
  if (!seedData) {
5410
- logger$3('[db/queries] [getItem] no seedData seedUid', seedUid);
5237
+ logger$4('[db/queries] [getItem] no seedData seedUid', seedUid);
5411
5238
  return;
5412
5239
  }
5413
5240
  seedLocalId = seedData.localId;
@@ -5550,17 +5377,30 @@ class Item {
5550
5377
  });
5551
5378
  }
5552
5379
  static create(props) {
5553
- if (props.seedUid) {
5554
- if (this.instanceCache.has(props.seedUid)) {
5555
- const { instance, refCount } = this.instanceCache.get(props.seedUid);
5556
- this.instanceCache.set(props.seedUid, {
5380
+ if (props.seedUid || props.seedLocalId) {
5381
+ const seedId = props.seedUid || props.seedLocalId;
5382
+ if (Item.instanceCache.has(seedId)) {
5383
+ const { instance, refCount } = Item.instanceCache.get(seedId);
5384
+ Item.instanceCache.set(seedId, {
5557
5385
  instance,
5558
5386
  refCount: refCount + 1,
5559
5387
  });
5560
5388
  return instance;
5561
5389
  }
5390
+ if (!Item.instanceCache.has(props.seedLocalId)) {
5391
+ const newInstance = new Item(props);
5392
+ Item.instanceCache.set(seedId, {
5393
+ instance: newInstance,
5394
+ refCount: 1,
5395
+ });
5396
+ return newInstance;
5397
+ }
5562
5398
  }
5563
5399
  const newInstance = new Item(props);
5400
+ Item.instanceCache.set(newInstance.seedUid || newInstance.seedLocalId, {
5401
+ instance: newInstance,
5402
+ refCount: 1,
5403
+ });
5564
5404
  return newInstance;
5565
5405
  }
5566
5406
  static find(_b) {
@@ -5705,362 +5545,44 @@ const GET_ALL_PROPERTIES_FOR_ALL_VERSIONS = graphql(/* GraphQL */ `
5705
5545
  }
5706
5546
  `);
5707
5547
 
5708
- const logger$2 = debug('app:react:index');
5709
- const useItemProperty = (propertyName, seedLocalId) => {
5710
- const [property, setProperty] = useImmer(undefined);
5711
- const [isReadingFromDb, setIsReadingFromDb] = useState(false);
5712
- const [isInitialized, setIsInitialized] = useState(false);
5713
- const value = useSelector(property === null || property === void 0 ? void 0 : property.getService(), (snapshot) => {
5714
- if (!snapshot || !snapshot.context) {
5715
- return;
5716
- }
5717
- return snapshot.context.renderValue || snapshot.context.propertyValue;
5718
- });
5719
- const status = useSelector(property === null || property === void 0 ? void 0 : property.getService(), (snapshot) => snapshot === null || snapshot === void 0 ? void 0 : snapshot.value);
5720
- useEffect(() => {
5721
- if (property && property.value !== value) {
5722
- readFromDb();
5723
- }
5724
- }, [property, value]);
5725
- const readFromDb = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
5726
- if (isReadingFromDb) {
5727
- return;
5728
- }
5729
- setIsReadingFromDb(true);
5730
- const foundProperty = yield ItemProperty.find({ propertyName, seedLocalId });
5731
- setIsReadingFromDb(false);
5732
- if (!foundProperty) {
5733
- logger$2(`[useItemPropertyTest] [readFromDb] no property found for Item.${seedLocalId}.${propertyName}`);
5734
- return;
5735
- }
5736
- setProperty(() => foundProperty);
5737
- setIsInitialized(true);
5738
- }), [isReadingFromDb]);
5739
- useEffect(() => {
5740
- readFromDb();
5741
- }, []);
5742
- // TODO: How can we force a re-render when the property is updated?
5743
- // Right now, the value will trigger an update because it's using a selector
5744
- // and a change is pushed to the hook listener.
5745
- return {
5746
- property,
5747
- isInitialized,
5748
- isReadingFromDb,
5749
- value,
5750
- status,
5751
- };
5752
- };
5753
- const useItem = ({ modelName, seedLocalId, seedUid }) => {
5754
- const [item, setItem] = useImmer(undefined);
5755
- const [isReadingFromDb, setIsReadingFromDb] = useState(false);
5756
- const [itemSubscription, setItemSubscription] = useState();
5757
- const { status, internalStatus } = useGlobalServiceStatus();
5758
- const context = useSelector(item === null || item === void 0 ? void 0 : item.getService(), (snapshot) => snapshot === null || snapshot === void 0 ? void 0 : snapshot.context);
5759
- const updateItem = useCallback((newItem) => {
5760
- setItem(() => newItem);
5761
- }, []);
5762
- const readFromDb = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
5763
- if (internalStatus !== 'ready' ||
5764
- (!seedUid && !seedLocalId) ||
5765
- isReadingFromDb) {
5766
- return;
5767
- }
5768
- const foundItem = yield Item.find({
5769
- modelName,
5770
- seedLocalId,
5771
- seedUid,
5772
- });
5773
- if (!foundItem) {
5774
- logger$2('[useItem] [getItemFromDb] no item found', modelName, seedLocalId);
5775
- return;
5776
- }
5777
- updateItem(foundItem);
5778
- }), [internalStatus, isReadingFromDb]);
5779
- useEffect(() => {
5780
- if (internalStatus === 'ready') {
5781
- readFromDb();
5782
- }
5783
- }, [internalStatus, status]);
5784
- useEffect(() => {
5785
- if (item && !itemSubscription) {
5786
- const subscription = item.subscribe((_) => __awaiter(void 0, void 0, void 0, function* () {
5787
- const newItem = yield Item.find({ modelName, seedLocalId, seedUid });
5788
- if (!newItem) {
5789
- logger$2('[useItem] [itemSubscription] no item found', modelName, seedLocalId);
5790
- return;
5791
- }
5792
- setItem(() => newItem);
5793
- }));
5794
- setItemSubscription(subscription);
5795
- }
5796
- return () => {
5797
- itemSubscription === null || itemSubscription === void 0 ? void 0 : itemSubscription.unsubscribe();
5798
- };
5799
- }, [item, itemSubscription]);
5800
- useEffect(() => {
5801
- const seedId = seedUid || seedLocalId;
5802
- eventEmitter.addListener(`item.${modelName}.${seedId}.update`, readFromDb);
5803
- return () => {
5804
- eventEmitter.removeListener(`item.${modelName}.${seedId}.update`, readFromDb);
5805
- };
5806
- }, []);
5548
+ const getVersionData = (_a) => __awaiter(void 0, [_a], void 0, function* ({ seedLocalId }) {
5549
+ const getVersionStatement = `SELECT local_id,
5550
+ uid,
5551
+ seed_local_id,
5552
+ seed_uid,
5553
+ seed_type,
5554
+ note,
5555
+ attestation_created_at,
5556
+ attestation_raw,
5557
+ created_at,
5558
+ updated_at
5559
+ FROM versions
5560
+ WHERE local_id = '${seedLocalId}';`;
5561
+ const { rows } = yield runQueryForStatement(getVersionStatement);
5562
+ if (!rows || !rows.length) {
5563
+ return;
5564
+ }
5565
+ const seedValues = rows[0];
5807
5566
  return {
5808
- item,
5809
- isReadingFromDb,
5810
- context,
5567
+ localId: seedValues[0],
5568
+ uid: seedValues[1],
5569
+ seedLocalId: seedValues[2],
5570
+ seedUid: seedValues[3],
5571
+ seedType: seedValues[4],
5572
+ note: seedValues[5],
5573
+ attestationCreatedAt: seedValues[6],
5574
+ attestationRaw: seedValues[7],
5575
+ createdAt: seedValues[8],
5576
+ updatedAt: seedValues[9],
5811
5577
  };
5812
- };
5813
- const useItems = ({ modelName, options }) => {
5814
- const [items, setItems] = useImmer([]);
5815
- const [isReadingDb, setIsReadingDb] = useState(false);
5816
- const [isInitialized, setIsInitialized] = useState(false);
5817
- const { dbsAreReady } = useDbsAreReady();
5818
- const modelNameRef = useRef(modelName);
5819
- const refresh = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
5820
- eventEmitter.emit('item.requestAll', { modelName });
5821
- }), []);
5822
- const readFromDb = useCallback((event) => __awaiter(void 0, void 0, void 0, function* () {
5823
- if (!event ||
5824
- !event.modelName ||
5825
- event.modelName !== modelNameRef.current ||
5826
- isReadingDb) {
5827
- return;
5828
- }
5829
- setIsReadingDb(true);
5830
- const allItems = yield Item.all(modelNameRef.current);
5831
- setItems(() => allItems);
5832
- setIsReadingDb(false);
5833
- }), [modelName]);
5834
- useEffect(() => {
5835
- if (dbsAreReady && !isInitialized) {
5836
- const _fetchItems = () => __awaiter(void 0, void 0, void 0, function* () {
5837
- yield readFromDb({ modelName });
5838
- setIsInitialized(true);
5839
- });
5840
- _fetchItems();
5841
- }
5842
- }, [dbsAreReady, isInitialized]);
5843
- useEffect(() => {
5844
- eventEmitter.addListener('item.requestAll', readFromDb);
5845
- return () => {
5846
- eventEmitter.removeListener('item.requestAll');
5847
- };
5848
- }, []);
5849
- return {
5850
- items: orderBy(items, [
5851
- (item) => item.lastVersionPublishedAt ||
5852
- item.attestationCreatedAt ||
5853
- item.createdAt,
5854
- ], ['desc']),
5855
- isReadingDb,
5856
- isInitialized,
5857
- refresh,
5858
- };
5859
- };
5860
- const useDbsAreReady = () => {
5861
- const [dbsAreReady, setDbsAreReady] = useState(false);
5862
- const update = useCallback(() => {
5863
- if (dbsAreReady) {
5864
- return;
5865
- }
5866
- setDbsAreReady(true);
5867
- }, []);
5868
- useEffect(() => {
5869
- let globalSubscription;
5870
- let internalSubscription;
5871
- const _waitForDbs = () => __awaiter(void 0, void 0, void 0, function* () {
5872
- const globalService = getGlobalService();
5873
- const internalService = globalService.getSnapshot().context.internalService;
5874
- if (!internalService) {
5875
- logger$2('[useDbsAreReady] [useEffect] no internalService');
5876
- globalSubscription = globalService.subscribe(({ context }) => {
5877
- if (!internalSubscription && context && context.internalService) {
5878
- globalSubscription === null || globalSubscription === void 0 ? void 0 : globalSubscription.unsubscribe();
5879
- internalSubscription = context.internalService.subscribe((snapshot) => {
5880
- if (snapshot.value === 'ready') {
5881
- update();
5882
- internalSubscription === null || internalSubscription === void 0 ? void 0 : internalSubscription.unsubscribe();
5883
- }
5884
- });
5885
- }
5886
- });
5887
- return;
5888
- }
5889
- const currentState = internalService.getSnapshot().value;
5890
- if (currentState === 'ready') {
5891
- update();
5892
- return;
5893
- }
5894
- internalSubscription = internalService.subscribe((snapshot) => {
5895
- if (snapshot.value === 'ready') {
5896
- update();
5897
- internalSubscription === null || internalSubscription === void 0 ? void 0 : internalSubscription.unsubscribe();
5898
- }
5899
- });
5900
- });
5901
- _waitForDbs();
5902
- return () => {
5903
- if (globalSubscription) {
5904
- globalSubscription.unsubscribe();
5905
- }
5906
- if (internalSubscription) {
5907
- internalSubscription.unsubscribe();
5908
- }
5909
- };
5910
- }, []);
5911
- return {
5912
- dbsAreReady,
5913
- };
5914
- };
5915
- const useItemIsReady = () => {
5916
- const [itemListenersReady, setItemListenersReady] = useState(false);
5917
- const itemEventListenersHandler = useCallback((_) => {
5918
- setItemListenersReady(true);
5919
- }, []);
5920
- useEffect(() => {
5921
- const areReady = getAreItemEventHandlersReady();
5922
- if (areReady) {
5923
- itemEventListenersHandler(true);
5924
- }
5925
- eventEmitter.addListener('item.events.setupAllItemsEventHandlers', itemEventListenersHandler);
5926
- return () => {
5927
- eventEmitter.removeListener('item.events.setupAllItemsEventHandlers');
5928
- };
5929
- }, []);
5930
- return {
5931
- isReady: itemListenersReady,
5932
- };
5933
- };
5934
- const useItemProperties = (item) => {
5935
- const [propertyObj, setPropertyObj] = useImmer({});
5936
- useState(false);
5937
- const updatePropertyObj = useCallback((event) => {
5938
- if (!item) {
5939
- console.error('[XXXXXX] [updatePropertyObj] no item when expected');
5940
- return;
5941
- }
5942
- const { propertyName, propertyValue } = event;
5943
- if (!propertyName) {
5944
- return;
5945
- }
5946
- setPropertyObj((draft) => {
5947
- draft[propertyName] = propertyValue;
5948
- });
5949
- }, [item]);
5950
- useEffect(() => {
5951
- if (!item) {
5952
- return;
5953
- }
5954
- const eventKey = `item.${item.seedLocalId}.property.update`;
5955
- eventEmitter.addListener(eventKey, updatePropertyObj);
5956
- return () => {
5957
- eventEmitter.removeListener(eventKey, updatePropertyObj);
5958
- };
5959
- }, [item]);
5960
- return {
5961
- properties: propertyObj,
5962
- };
5963
- };
5964
- const useCreateItem = (modelName) => {
5965
- const [isCreatingItem, setIsCreatingItem] = useState(false);
5966
- const { isReady } = useItemIsReady();
5967
- const createItem = useCallback((itemData) => __awaiter(void 0, void 0, void 0, function* () {
5968
- if (!isReady) {
5969
- console.error(`[useCreateItem] [createItem] called before listeners are ready`, itemData);
5970
- return;
5971
- }
5972
- if (isCreatingItem) {
5973
- // TODO: should we setup a queue for this?
5974
- console.error(`[useCreateItem] [createItem] already creating item`, itemData);
5975
- return;
5976
- }
5977
- setIsCreatingItem(true);
5978
- const { seedLocalId } = yield createNewItem(Object.assign({ modelName }, itemData));
5979
- yield Item.find({ modelName, seedLocalId });
5980
- eventEmitter.emit('item.requestAll', { modelName });
5981
- setIsCreatingItem(false);
5982
- }), [isCreatingItem, isReady]);
5983
- return {
5984
- createItem,
5985
- isCreatingItem,
5986
- };
5987
- };
5988
- const useDeleteItem = () => {
5989
- const [isDeletingItem, setIsDeletingItem] = useState(false);
5990
- const destroy = useCallback((item) => __awaiter(void 0, void 0, void 0, function* () {
5991
- if (!item) {
5992
- return;
5993
- }
5994
- setIsDeletingItem(true);
5995
- const { modelName } = item.getService().getSnapshot().context;
5996
- yield deleteItem({ seedLocalId: item.seedLocalId });
5997
- eventEmitter.emit('item.requestAll', { modelName });
5998
- setIsDeletingItem(false);
5999
- }), [isDeletingItem]);
6000
- useEffect(() => { }, []);
6001
- return {
6002
- deleteItem: destroy,
6003
- isDeletingItem,
6004
- };
6005
- };
6006
- const useGlobalServiceStatus = () => {
6007
- const globalService = getGlobalService();
6008
- const status = useSelector(globalService, (snapshot) => {
6009
- return snapshot.value;
6010
- });
6011
- const internalStatus = useSelector(globalService.getSnapshot().context.internalService, (snapshot) => {
6012
- if (!snapshot) {
6013
- return;
6014
- }
6015
- return snapshot.value;
6016
- });
6017
- useSelector(globalService, (snapshot) => {
6018
- return snapshot.context.internalService;
6019
- });
6020
- return {
6021
- status,
6022
- internalStatus,
6023
- };
6024
- };
6025
-
6026
- const getVersionData = (_a) => __awaiter(void 0, [_a], void 0, function* ({ seedLocalId }) {
6027
- const getVersionStatement = `SELECT local_id,
6028
- uid,
6029
- seed_local_id,
6030
- seed_uid,
6031
- seed_type,
6032
- note,
6033
- attestation_created_at,
6034
- attestation_raw,
6035
- created_at,
6036
- updated_at
6037
- FROM versions
6038
- WHERE local_id = '${seedLocalId}';`;
6039
- const { rows } = yield runQueryForStatement(getVersionStatement);
6040
- if (!rows || !rows.length) {
6041
- return;
6042
- }
6043
- const seedValues = rows[0];
6044
- return {
6045
- localId: seedValues[0],
6046
- uid: seedValues[1],
6047
- seedLocalId: seedValues[2],
6048
- seedUid: seedValues[3],
6049
- seedType: seedValues[4],
6050
- note: seedValues[5],
6051
- attestationCreatedAt: seedValues[6],
6052
- attestationRaw: seedValues[7],
6053
- createdAt: seedValues[8],
6054
- updatedAt: seedValues[9],
6055
- };
6056
- });
6057
-
6058
- const logger$1 = debug('app:write');
6059
- const sendItemUpdateEvent = ({ modelName, seedLocalId, seedUid }) => {
6060
- if (!modelName || (!seedLocalId && !seedUid)) {
6061
- return;
6062
- }
6063
- eventEmitter.emit(`item.${modelName}.${seedUid || seedLocalId}.update`);
5578
+ });
5579
+
5580
+ const logger$3 = debug('app:write');
5581
+ const sendItemUpdateEvent = ({ modelName, seedLocalId, seedUid }) => {
5582
+ if (!modelName || (!seedLocalId && !seedUid)) {
5583
+ return;
5584
+ }
5585
+ eventEmitter.emit(`item.${modelName}.${seedUid || seedLocalId}.update`);
6064
5586
  };
6065
5587
  const createSeed = (_a) => __awaiter(void 0, [_a], void 0, function* ({ type }) {
6066
5588
  const appDb = getAppDb();
@@ -6133,7 +5655,7 @@ const deleteItem = (_a) => __awaiter(void 0, [_a], void 0, function* ({ seedLoca
6133
5655
  });
6134
5656
  const updateItemPropertyValue = (_a) => __awaiter(void 0, [_a], void 0, function* ({ propertyLocalId, propertyName, newValue, seedUid, seedLocalId, modelName, refSeedType, refResolvedValue, refResolvedDisplayValue, versionLocalId, versionUid, schemaUid, }) {
6135
5657
  if (!propertyLocalId && !seedLocalId) {
6136
- logger$1(`[db/write] [updateItemPropertyValue] no propertyLocalId or seedLocalId for property: ${propertyName}`);
5658
+ logger$3(`[db/write] [updateItemPropertyValue] no propertyLocalId or seedLocalId for property: ${propertyName}`);
6137
5659
  return;
6138
5660
  }
6139
5661
  let safeNewValue = newValue;
@@ -6172,7 +5694,7 @@ const updateItemPropertyValue = (_a) => __awaiter(void 0, [_a], void 0, function
6172
5694
  const schemaUid = mostRecentRecord[9];
6173
5695
  const easDataType = mostRecentRecord[10];
6174
5696
  if (propertyValueFromDb === newValue) {
6175
- logger$1(`[db/write] [updateItemPropertyValue] value is the same as most recent record for property: ${propertyNameFromDb}`);
5697
+ logger$3(`[db/write] [updateItemPropertyValue] value is the same as most recent record for property: ${propertyNameFromDb}`);
6176
5698
  return;
6177
5699
  }
6178
5700
  // This means we already have a local-only record so we should just update that one
@@ -6268,39 +5790,487 @@ const updateItemPropertyValue = (_a) => __awaiter(void 0, [_a], void 0, function
6268
5790
  sendItemUpdateEvent({ modelName, seedLocalId, seedUid });
6269
5791
  });
6270
5792
 
6271
- const saveValueToDb = fromCallback(({ sendBack, input: { context, event } }) => {
6272
- const { localId, propertyName: propertyNameRaw, seedLocalId, propertyValue: existingValue, propertyRecordSchema, itemModelName, schemaUid, } = context;
6273
- let { newValue } = event;
6274
- if (existingValue === newValue) {
6275
- sendBack({ type: 'saveValueToDbSuccess' });
6276
- return;
6277
- }
6278
- const _saveValueToDb = () => __awaiter(void 0, void 0, void 0, function* () {
6279
- let refResolvedValue;
6280
- let refResolvedDisplayValue;
6281
- let refSeedType;
6282
- let propertyName = propertyNameRaw;
6283
- let versionLocalId;
6284
- if (propertyRecordSchema &&
6285
- propertyRecordSchema.dataType === 'Relation') {
6286
- refResolvedValue = newValue;
6287
- if (!propertyName.endsWith('Id')) {
6288
- propertyName = `${propertyName}Id`;
6289
- }
6290
- let fileType;
6291
- const dirs = yield fs.promises.readdir('/files');
6292
- for (const dir of dirs) {
6293
- const files = yield fs.promises.readdir(`/files/${dir}`);
6294
- if (files.includes(newValue)) {
6295
- fileType = dir;
6296
- break;
6297
- }
6298
- }
6299
- if (fileType === 'images') {
6300
- const filePath = `/files/images/${newValue}`;
6301
- refResolvedDisplayValue = yield getContentUrlFromPath(filePath);
6302
- refSeedType = 'image';
6303
- newValue = yield createSeed({
5793
+ const logger$2 = debug('app:react:index');
5794
+ const useItemProperty = (propertyName, seedLocalId) => {
5795
+ const [property, setProperty] = useImmer(undefined);
5796
+ const [isReadingFromDb, setIsReadingFromDb] = useState(false);
5797
+ const [isInitialized, setIsInitialized] = useState(false);
5798
+ const value = useSelector(property === null || property === void 0 ? void 0 : property.getService(), (snapshot) => {
5799
+ if (!snapshot || !snapshot.context) {
5800
+ return;
5801
+ }
5802
+ return snapshot.context.renderValue || snapshot.context.propertyValue;
5803
+ });
5804
+ const status = useSelector(property === null || property === void 0 ? void 0 : property.getService(), (snapshot) => snapshot === null || snapshot === void 0 ? void 0 : snapshot.value);
5805
+ useEffect(() => {
5806
+ if (property && property.value !== value) {
5807
+ readFromDb();
5808
+ }
5809
+ }, [property, value]);
5810
+ const readFromDb = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
5811
+ if (isReadingFromDb) {
5812
+ return;
5813
+ }
5814
+ setIsReadingFromDb(true);
5815
+ const foundProperty = yield ItemProperty.find({ propertyName, seedLocalId });
5816
+ setIsReadingFromDb(false);
5817
+ if (!foundProperty) {
5818
+ logger$2(`[useItemPropertyTest] [readFromDb] no property found for Item.${seedLocalId}.${propertyName}`);
5819
+ return;
5820
+ }
5821
+ setProperty(() => foundProperty);
5822
+ setIsInitialized(true);
5823
+ }), [isReadingFromDb]);
5824
+ useEffect(() => {
5825
+ readFromDb();
5826
+ }, []);
5827
+ // TODO: How can we force a re-render when the property is updated?
5828
+ // Right now, the value will trigger an update because it's using a selector
5829
+ // and a change is pushed to the hook listener.
5830
+ return {
5831
+ property,
5832
+ isInitialized,
5833
+ isReadingFromDb,
5834
+ value,
5835
+ status,
5836
+ };
5837
+ };
5838
+ const useItem = ({ modelName, seedLocalId, seedUid }) => {
5839
+ const [item, setItem] = useImmer(undefined);
5840
+ const [itemSubscription, setItemSubscription] = useState();
5841
+ const { status, internalStatus } = useGlobalServiceStatus();
5842
+ const isReadingDb = useRef(false);
5843
+ const itemStatus = useSelector(item === null || item === void 0 ? void 0 : item.getService(), (snapshot) => snapshot === null || snapshot === void 0 ? void 0 : snapshot.value);
5844
+ const updateItem = useCallback((newItem) => {
5845
+ setItem(() => newItem);
5846
+ }, []);
5847
+ const readFromDb = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
5848
+ if (isReadingDb.current ||
5849
+ internalStatus !== 'ready' ||
5850
+ (!seedUid && !seedLocalId)) {
5851
+ return;
5852
+ }
5853
+ isReadingDb.current = true;
5854
+ const foundItem = yield Item.find({
5855
+ modelName,
5856
+ seedLocalId,
5857
+ seedUid,
5858
+ });
5859
+ if (!foundItem) {
5860
+ logger$2('[useItem] [getItemFromDb] no item found', modelName, seedLocalId);
5861
+ return;
5862
+ }
5863
+ updateItem(foundItem);
5864
+ isReadingDb.current = false;
5865
+ }), [internalStatus]);
5866
+ useEffect(() => {
5867
+ if (internalStatus === 'ready') {
5868
+ readFromDb();
5869
+ }
5870
+ }, [internalStatus, status]);
5871
+ useEffect(() => {
5872
+ if (item && !itemSubscription) {
5873
+ const subscription = item.subscribe((_) => __awaiter(void 0, void 0, void 0, function* () {
5874
+ const newItem = yield Item.find({ modelName, seedLocalId, seedUid });
5875
+ if (!newItem) {
5876
+ logger$2('[useItem] [itemSubscription] no item found', modelName, seedLocalId);
5877
+ return;
5878
+ }
5879
+ setItem(() => newItem);
5880
+ }));
5881
+ setItemSubscription(subscription);
5882
+ }
5883
+ return () => {
5884
+ itemSubscription === null || itemSubscription === void 0 ? void 0 : itemSubscription.unsubscribe();
5885
+ };
5886
+ }, [item, itemSubscription]);
5887
+ useEffect(() => {
5888
+ const seedId = seedUid || seedLocalId;
5889
+ eventEmitter.addListener(`item.${modelName}.${seedId}.update`, readFromDb);
5890
+ return () => {
5891
+ eventEmitter.removeListener(`item.${modelName}.${seedId}.update`, readFromDb);
5892
+ };
5893
+ }, []);
5894
+ return {
5895
+ item,
5896
+ itemStatus,
5897
+ };
5898
+ };
5899
+ const useItems = ({ modelName, options }) => {
5900
+ const [items, setItems] = useImmer([]);
5901
+ const [isReadingDb, setIsReadingDb] = useState(false);
5902
+ const [isInitialized, setIsInitialized] = useState(false);
5903
+ const { dbsAreReady } = useDbsAreReady();
5904
+ const modelNameRef = useRef(modelName);
5905
+ const readFromDb = useCallback((event) => __awaiter(void 0, void 0, void 0, function* () {
5906
+ if (!event ||
5907
+ !event.modelName ||
5908
+ event.modelName !== modelNameRef.current ||
5909
+ isReadingDb) {
5910
+ return;
5911
+ }
5912
+ setIsReadingDb(true);
5913
+ const allItems = yield Item.all(modelNameRef.current);
5914
+ setItems(() => allItems);
5915
+ setIsReadingDb(false);
5916
+ }), [modelName]);
5917
+ useEffect(() => {
5918
+ if (dbsAreReady && !isInitialized) {
5919
+ const _fetchItems = () => __awaiter(void 0, void 0, void 0, function* () {
5920
+ yield readFromDb({ modelName });
5921
+ setIsInitialized(true);
5922
+ });
5923
+ _fetchItems();
5924
+ }
5925
+ }, [dbsAreReady, isInitialized]);
5926
+ useEffect(() => {
5927
+ eventEmitter.addListener('item.requestAll', readFromDb);
5928
+ return () => {
5929
+ eventEmitter.removeListener('item.requestAll');
5930
+ };
5931
+ }, []);
5932
+ return {
5933
+ items: orderBy(items, [
5934
+ (item) => item.lastVersionPublishedAt ||
5935
+ item.attestationCreatedAt ||
5936
+ item.createdAt,
5937
+ ], ['desc']).slice(0, 10),
5938
+ isReadingDb,
5939
+ isInitialized,
5940
+ };
5941
+ };
5942
+ const useDbsAreReady = () => {
5943
+ const [dbsAreReady, setDbsAreReady] = useState(false);
5944
+ const update = useCallback(() => {
5945
+ if (dbsAreReady) {
5946
+ return;
5947
+ }
5948
+ setDbsAreReady(true);
5949
+ }, []);
5950
+ useEffect(() => {
5951
+ let globalSubscription;
5952
+ let internalSubscription;
5953
+ const _waitForDbs = () => __awaiter(void 0, void 0, void 0, function* () {
5954
+ const globalService = getGlobalService();
5955
+ const internalService = globalService.getSnapshot().context.internalService;
5956
+ if (!internalService) {
5957
+ logger$2('[useDbsAreReady] [useEffect] no internalService');
5958
+ globalSubscription = globalService.subscribe(({ context }) => {
5959
+ if (!internalSubscription && context && context.internalService) {
5960
+ globalSubscription === null || globalSubscription === void 0 ? void 0 : globalSubscription.unsubscribe();
5961
+ internalSubscription = context.internalService.subscribe((snapshot) => {
5962
+ if (snapshot.value === 'ready') {
5963
+ update();
5964
+ internalSubscription === null || internalSubscription === void 0 ? void 0 : internalSubscription.unsubscribe();
5965
+ }
5966
+ });
5967
+ }
5968
+ });
5969
+ return;
5970
+ }
5971
+ const currentState = internalService.getSnapshot().value;
5972
+ if (currentState === 'ready') {
5973
+ update();
5974
+ return;
5975
+ }
5976
+ internalSubscription = internalService.subscribe((snapshot) => {
5977
+ if (snapshot.value === 'ready') {
5978
+ update();
5979
+ internalSubscription === null || internalSubscription === void 0 ? void 0 : internalSubscription.unsubscribe();
5980
+ }
5981
+ });
5982
+ });
5983
+ _waitForDbs();
5984
+ return () => {
5985
+ if (globalSubscription) {
5986
+ globalSubscription.unsubscribe();
5987
+ }
5988
+ if (internalSubscription) {
5989
+ internalSubscription.unsubscribe();
5990
+ }
5991
+ };
5992
+ }, []);
5993
+ return {
5994
+ dbsAreReady,
5995
+ };
5996
+ };
5997
+ const useItemIsReady = () => {
5998
+ const [itemListenersReady, setItemListenersReady] = useState(false);
5999
+ const itemEventListenersHandler = useCallback((_) => {
6000
+ setItemListenersReady(true);
6001
+ }, []);
6002
+ useEffect(() => {
6003
+ const areReady = getAreItemEventHandlersReady();
6004
+ if (areReady) {
6005
+ itemEventListenersHandler(true);
6006
+ }
6007
+ eventEmitter.addListener('item.events.setupAllItemsEventHandlers', itemEventListenersHandler);
6008
+ return () => {
6009
+ eventEmitter.removeListener('item.events.setupAllItemsEventHandlers');
6010
+ };
6011
+ }, []);
6012
+ return {
6013
+ isReady: itemListenersReady,
6014
+ };
6015
+ };
6016
+ const useItemProperties = (item) => {
6017
+ const [propertyObj, setPropertyObj] = useImmer({});
6018
+ useState(false);
6019
+ const updatePropertyObj = useCallback((event) => {
6020
+ if (!item) {
6021
+ console.error('[XXXXXX] [updatePropertyObj] no item when expected');
6022
+ return;
6023
+ }
6024
+ const { propertyName, propertyValue } = event;
6025
+ if (!propertyName) {
6026
+ return;
6027
+ }
6028
+ setPropertyObj((draft) => {
6029
+ draft[propertyName] = propertyValue;
6030
+ });
6031
+ }, [item]);
6032
+ useEffect(() => {
6033
+ if (!item) {
6034
+ return;
6035
+ }
6036
+ const eventKey = `item.${item.seedLocalId}.property.update`;
6037
+ eventEmitter.addListener(eventKey, updatePropertyObj);
6038
+ return () => {
6039
+ eventEmitter.removeListener(eventKey, updatePropertyObj);
6040
+ };
6041
+ }, [item]);
6042
+ return {
6043
+ properties: propertyObj,
6044
+ };
6045
+ };
6046
+ const useCreateItem = (modelName) => {
6047
+ const [isCreatingItem, setIsCreatingItem] = useState(false);
6048
+ const { isReady } = useItemIsReady();
6049
+ const createItem = useCallback((itemData) => __awaiter(void 0, void 0, void 0, function* () {
6050
+ if (!isReady) {
6051
+ console.error(`[useCreateItem] [createItem] called before listeners are ready`, itemData);
6052
+ return;
6053
+ }
6054
+ if (isCreatingItem) {
6055
+ // TODO: should we setup a queue for this?
6056
+ console.error(`[useCreateItem] [createItem] already creating item`, itemData);
6057
+ return;
6058
+ }
6059
+ setIsCreatingItem(true);
6060
+ const { seedLocalId } = yield createNewItem(Object.assign({ modelName }, itemData));
6061
+ yield Item.find({ modelName, seedLocalId });
6062
+ eventEmitter.emit('item.requestAll', { modelName });
6063
+ setIsCreatingItem(false);
6064
+ }), [isCreatingItem, isReady]);
6065
+ return {
6066
+ createItem,
6067
+ isCreatingItem,
6068
+ };
6069
+ };
6070
+ const useDeleteItem = () => {
6071
+ const [isDeletingItem, setIsDeletingItem] = useState(false);
6072
+ const destroy = useCallback((item) => __awaiter(void 0, void 0, void 0, function* () {
6073
+ if (!item) {
6074
+ return;
6075
+ }
6076
+ setIsDeletingItem(true);
6077
+ const { modelName } = item.getService().getSnapshot().context;
6078
+ yield deleteItem({ seedLocalId: item.seedLocalId });
6079
+ eventEmitter.emit('item.requestAll', { modelName });
6080
+ setIsDeletingItem(false);
6081
+ }), [isDeletingItem]);
6082
+ useEffect(() => { }, []);
6083
+ return {
6084
+ deleteItem: destroy,
6085
+ isDeletingItem,
6086
+ };
6087
+ };
6088
+ const useGlobalServiceStatus = () => {
6089
+ const globalService = getGlobalService();
6090
+ const status = useSelector(globalService, (snapshot) => {
6091
+ return snapshot.value;
6092
+ });
6093
+ const internalStatus = useSelector(globalService.getSnapshot().context.internalService, (snapshot) => {
6094
+ if (!snapshot) {
6095
+ return;
6096
+ }
6097
+ return snapshot.value;
6098
+ });
6099
+ useSelector(globalService, (snapshot) => {
6100
+ return snapshot.context.internalService;
6101
+ });
6102
+ return {
6103
+ status,
6104
+ internalStatus,
6105
+ };
6106
+ };
6107
+
6108
+ const logger$1 = debug('app:property:actors:hydrateFromDb');
6109
+ const hydrateFromDb = fromCallback(({ sendBack, input: { context } }) => {
6110
+ const { seedUid, seedLocalId, propertyName: propertyNameRaw, propertyValue, propertyRecordSchema, itemModelName, } = context;
6111
+ let propertyName = propertyNameRaw;
6112
+ if (propertyRecordSchema &&
6113
+ propertyRecordSchema.ref &&
6114
+ propertyRecordSchema.dataType === 'Relation' &&
6115
+ !propertyNameRaw.endsWith('Id')) {
6116
+ propertyName = propertyNameRaw + 'Id';
6117
+ }
6118
+ if (propertyRecordSchema &&
6119
+ propertyRecordSchema.ref &&
6120
+ propertyRecordSchema.dataType === 'List' &&
6121
+ !propertyNameRaw.endsWith('Ids')) {
6122
+ propertyName = propertyNameRaw + 'Ids';
6123
+ }
6124
+ const _hydrateFromDb = () => __awaiter(void 0, void 0, void 0, function* () {
6125
+ const db = getAppDb();
6126
+ let hydrateQuery;
6127
+ let safeValue = propertyValue;
6128
+ let propertyNameQuery = eq(metadata.propertyName, propertyName);
6129
+ if (safeValue && typeof propertyValue === 'string') {
6130
+ safeValue = escapeSqliteString(propertyValue);
6131
+ }
6132
+ if (propertyRecordSchema &&
6133
+ propertyRecordSchema.ref &&
6134
+ propertyRecordSchema.dataType === 'Relation') {
6135
+ let missingPropertyNameVariant;
6136
+ if (propertyName.endsWith('Id')) {
6137
+ missingPropertyNameVariant = propertyName.slice(0, -2);
6138
+ }
6139
+ if (!propertyName.endsWith('Id')) {
6140
+ missingPropertyNameVariant = propertyName + 'Id';
6141
+ }
6142
+ propertyNameQuery = or(eq(metadata.propertyName, propertyName), eq(metadata.propertyName, missingPropertyNameVariant));
6143
+ }
6144
+ const selectFromStatement = db
6145
+ .select({
6146
+ localId: metadata.localId,
6147
+ uid: metadata.uid,
6148
+ propertyName: metadata.propertyName,
6149
+ propertyValue: metadata.propertyValue,
6150
+ seedLocalId: metadata.seedLocalId,
6151
+ seedUid: metadata.seedUid,
6152
+ schemaUid: metadata.schemaUid,
6153
+ refResolvedValue: metadata.refResolvedValue,
6154
+ refResolvedDisplayValue: metadata.refResolvedDisplayValue,
6155
+ })
6156
+ .from(metadata);
6157
+ if (seedUid && !seedLocalId) {
6158
+ hydrateQuery = selectFromStatement.where(and(eq(metadata.seedUid, seedUid), propertyNameQuery));
6159
+ }
6160
+ if (seedUid && seedLocalId) {
6161
+ hydrateQuery = selectFromStatement.where(and(eq(metadata.seedLocalId, seedLocalId), eq(metadata.seedUid, seedUid), propertyNameQuery));
6162
+ }
6163
+ if (!seedUid && seedLocalId) {
6164
+ hydrateQuery = selectFromStatement.where(and(eq(metadata.seedLocalId, seedLocalId), propertyNameQuery));
6165
+ }
6166
+ if (!hydrateQuery) {
6167
+ return;
6168
+ }
6169
+ const rows = yield hydrateQuery.orderBy(sql.raw('COALESCE(attestation_created_at, created_at) DESC'));
6170
+ if (!rows || !rows.length) {
6171
+ return;
6172
+ }
6173
+ const firstRow = rows[0];
6174
+ const { localId, uid, propertyName: propertyNameFromDb, propertyValue: propertyValueFromDb, seedLocalId: seedLocalIdFromDb, seedUid: seedUidFromDb, schemaUid: schemaUidFromDb, refResolvedValue, refResolvedDisplayValue, } = firstRow;
6175
+ if (propertyName && !propertyNameFromDb) {
6176
+ logger$1(`Property name from code is ${propertyName} but has not value in db ${propertyNameFromDb} for Property.${localId}`);
6177
+ }
6178
+ if (propertyName &&
6179
+ propertyNameFromDb &&
6180
+ !propertyNameFromDb.includes(propertyName) &&
6181
+ !propertyName.includes(propertyNameFromDb) &&
6182
+ propertyNameFromDb !== propertyName) {
6183
+ logger$1(`Property name from db ${propertyNameFromDb} does not match property name ${propertyName} for Property.${localId}`);
6184
+ }
6185
+ if (propertyValue && propertyValueFromDb !== propertyValue) {
6186
+ logger$1(`Property value from db ${propertyValueFromDb} does not match property value ${propertyValue} for Property.${localId}`);
6187
+ }
6188
+ if (seedLocalIdFromDb !== seedLocalId) {
6189
+ logger$1(`Seed local id from db ${seedLocalIdFromDb} does not match seed local id ${seedLocalId} for Property.${localId}`);
6190
+ }
6191
+ if (seedUidFromDb !== seedUid) {
6192
+ logger$1(`Seed uid from db ${seedUidFromDb} does not match seed uid ${seedUid} for Property.${localId}`);
6193
+ }
6194
+ sendBack({
6195
+ type: 'updateContext',
6196
+ localId,
6197
+ uid,
6198
+ propertyValue: propertyValueFromDb,
6199
+ seedLocalId: seedLocalIdFromDb,
6200
+ seedUid: seedUidFromDb,
6201
+ schemaUid: schemaUidFromDb,
6202
+ resolveValue: refResolvedValue,
6203
+ resolveDisplayValue: refResolvedDisplayValue,
6204
+ renderValue: refResolvedDisplayValue,
6205
+ });
6206
+ if (propertyNameFromDb === 'storageTransactionId') {
6207
+ const { Item } = yield import('./index-CXe0BS3G.js');
6208
+ const item = yield Item.find({
6209
+ seedLocalId,
6210
+ modelName: itemModelName,
6211
+ });
6212
+ if (item) {
6213
+ for (const [propertyName, property] of Object.entries(item.properties)) {
6214
+ if (propertyName === 'html' &&
6215
+ propertyValueFromDb &&
6216
+ propertyValueFromDb.length === 43) {
6217
+ const htmlFilePath = `/files/html/${propertyValueFromDb}.html`;
6218
+ const exists = yield fs.promises.exists(htmlFilePath);
6219
+ if (!exists) {
6220
+ return;
6221
+ }
6222
+ const renderValue = yield fs.promises
6223
+ .readFile(htmlFilePath, 'utf8')
6224
+ .catch((error) => {
6225
+ logger$1('Error reading html file', error);
6226
+ });
6227
+ property
6228
+ .getService()
6229
+ .send({ type: 'updateRenderValue', renderValue });
6230
+ return;
6231
+ }
6232
+ }
6233
+ }
6234
+ }
6235
+ });
6236
+ _hydrateFromDb().then(() => {
6237
+ sendBack({ type: 'hydrateFromDbSuccess' });
6238
+ });
6239
+ });
6240
+
6241
+ const saveValueToDb = fromCallback(({ sendBack, input: { context, event } }) => {
6242
+ const { localId, propertyName: propertyNameRaw, seedLocalId, propertyValue: existingValue, propertyRecordSchema, itemModelName, schemaUid, } = context;
6243
+ let { newValue } = event;
6244
+ if (existingValue === newValue) {
6245
+ sendBack({ type: 'saveValueToDbSuccess' });
6246
+ return;
6247
+ }
6248
+ const _saveValueToDb = () => __awaiter(void 0, void 0, void 0, function* () {
6249
+ let refResolvedValue;
6250
+ let refResolvedDisplayValue;
6251
+ let refSeedType;
6252
+ let propertyName = propertyNameRaw;
6253
+ let versionLocalId;
6254
+ if (propertyRecordSchema &&
6255
+ propertyRecordSchema.dataType === 'Relation') {
6256
+ refResolvedValue = newValue;
6257
+ if (!propertyName.endsWith('Id')) {
6258
+ propertyName = `${propertyName}Id`;
6259
+ }
6260
+ let fileType;
6261
+ const dirs = yield fs.promises.readdir('/files');
6262
+ for (const dir of dirs) {
6263
+ const files = yield fs.promises.readdir(`/files/${dir}`);
6264
+ if (files.includes(newValue)) {
6265
+ fileType = dir;
6266
+ break;
6267
+ }
6268
+ }
6269
+ if (fileType === 'images') {
6270
+ const filePath = `/files/images/${newValue}`;
6271
+ refResolvedDisplayValue = yield getContentUrlFromPath(filePath);
6272
+ refSeedType = 'image';
6273
+ newValue = yield createSeed({
6304
6274
  type: refSeedType,
6305
6275
  });
6306
6276
  versionLocalId = yield createVersion({
@@ -6323,7 +6293,6 @@ const saveValueToDb = fromCallback(({ sendBack, input: { context, event } }) =>
6323
6293
  });
6324
6294
  sendBack({
6325
6295
  type: 'updateContext',
6326
- isSaving: false,
6327
6296
  propertyValue: newValue,
6328
6297
  renderValue: refResolvedDisplayValue,
6329
6298
  });
@@ -6387,11 +6356,7 @@ const propertyMachine = setup({
6387
6356
  },
6388
6357
  },
6389
6358
  states: {
6390
- idle: {
6391
- on: {
6392
- refresh: 'hydratingFromDb',
6393
- },
6394
- },
6359
+ idle: {},
6395
6360
  waitingForDb: {
6396
6361
  on: {
6397
6362
  waitForDbSuccess: {
@@ -6403,6 +6368,7 @@ const propertyMachine = setup({
6403
6368
  },
6404
6369
  invoke: {
6405
6370
  src: 'waitForDb',
6371
+ input: ({ context }) => ({ context }),
6406
6372
  },
6407
6373
  },
6408
6374
  hydratingFromDb: {
@@ -6460,13 +6426,13 @@ const propertyMachine = setup({
6460
6426
  },
6461
6427
  saving: {
6462
6428
  on: {
6463
- saveSuccess: {
6429
+ saveValueToDbSuccess: {
6464
6430
  target: 'idle',
6465
6431
  actions: assign({
6466
6432
  isSaving: false,
6467
6433
  }),
6468
6434
  },
6469
- saveFailure: {
6435
+ saveValueToDbFailure: {
6470
6436
  target: 'idle',
6471
6437
  actions: assign({
6472
6438
  isSaving: false,
@@ -6899,7 +6865,7 @@ const client = {
6899
6865
  console.error('fs listeners not ready during init');
6900
6866
  }
6901
6867
  globalService.send({ type: 'init', endpoints, models, addresses });
6902
- import('./seed.schema.config-D7dRgRFf.js').then(({ models }) => {
6868
+ import('./seed.schema.config-Dg9Q0kx4.js').then(({ models }) => {
6903
6869
  for (const [key, value] of Object.entries(models)) {
6904
6870
  modelStore.set(key, value);
6905
6871
  }
@@ -6957,4 +6923,4 @@ const client = {
6957
6923
  };
6958
6924
 
6959
6925
  export { APP_DB_CONFIG as A, useCreateItem as B, CHILD_SNAPSHOT as C, DB_NAME_SDK_CONFIG as D, useItemProperty as E, useDeleteItem as F, GET_SCHEMAS as G, getGlobalService as H, Item as I, Json as J, getCorrectId as K, List as L, Model as M, Property as P, Relation as R, SCHEMA_NJK as S, Text as T, __decorate as _, GET_SEEDS as a, GET_SEED_IDS as b, GET_STORAGE_TRANSACTION_ID as c, GET_VERSIONS as d, GET_PROPERTIES as e, GET_ALL_PROPERTIES_FOR_ALL_VERSIONS as f, itemMachineAll as g, __metadata as h, itemMachineSingle as i, internalMachine as j, isNode as k, isBrowser as l, isReactNative as m, __awaiter as n, models as o, SCHEMA_TS as p, SDK_DB_CONFIG as q, SEED_DB_CONFIG as r, addModelsToInternalDb as s, client as t, ImageSrc as u, ItemProperty as v, withSeed as w, useItems as x, useItem as y, useItemProperties as z };
6960
- //# sourceMappingURL=index-C6vnbWlE.js.map
6926
+ //# sourceMappingURL=index-Dd2ggBQg.js.map