@atlaskit/editor-synced-block-provider 4.3.1 → 4.3.2

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.
@@ -14,17 +14,17 @@ import { SourceSyncBlockStoreManager } from './sourceSyncBlockStoreManager';
14
14
  // SourceSyncBlockStoreManager is responsible for the lifecycle and state management of source sync blocks in an editor instance.
15
15
  // Can be used in both editor and renderer contexts.
16
16
  export class SyncBlockStoreManager {
17
- constructor(dataProvider) {
17
+ constructor(dataProvider, viewMode) {
18
18
  // In future, if reference manager needs to reach to source manager and read its current in memory cache
19
19
  // we can pass the source manager as a parameter to the reference manager constructor
20
- this.sourceSyncBlockStoreManager = new SourceSyncBlockStoreManager(dataProvider);
21
- this.referenceSyncBlockStoreManager = new ReferenceSyncBlockStoreManager(dataProvider);
20
+ this.sourceSyncBlockStoreManager = new SourceSyncBlockStoreManager(dataProvider, viewMode);
21
+ this.referenceSyncBlockStoreManager = new ReferenceSyncBlockStoreManager(dataProvider, viewMode);
22
22
  this.dataProvider = dataProvider;
23
23
  this.referenceSyncBlockStoreManager.setRealTimeSubscriptionsEnabled(true);
24
24
  }
25
25
  async fetchReferencesSourceInfo(resourceId, blockInstanceId, isSourceSyncBlock) {
26
26
  try {
27
- var _this$fetchReferences, _response$references, _this$fetchReferences9, _response$references2;
27
+ var _this$fetchReferences, _response$references, _this$fetchReferences5, _response$references2;
28
28
  if (!this.dataProvider) {
29
29
  throw new Error('Data provider not set');
30
30
  }
@@ -41,94 +41,15 @@ export class SyncBlockStoreManager {
41
41
  }
42
42
  if (!response.references || ((_response$references = response.references) === null || _response$references === void 0 ? void 0 : _response$references.length) === 0) {
43
43
  if (fg('platform_synced_block_patch_8')) {
44
- // No reference found
45
- if (isSourceSyncBlock) {
46
- var _this$fetchReferences4;
47
- // Verify that a reference sync block for this specific source actually
48
- // exists on the current page by checking if the reference manager has
49
- // an active subscription for the derived reference resourceId.
50
- const referenceResourceId = this.referenceSyncBlockStoreManager.generateResourceIdForReference(resourceId);
51
- const hasUnregisteredReferenceOnPage = this.referenceSyncBlockStoreManager.getSubscribedResourceIds().includes(referenceResourceId);
52
- if (hasUnregisteredReferenceOnPage) {
53
- var _this$fetchReferences3;
54
- // This is current page data. It is the same for data for source and reference
55
- const sourceSyncBlockData = await this.sourceSyncBlockStoreManager.getSyncBlockSourceInfo(blockInstanceId);
56
- const references = [];
57
- if (sourceSyncBlockData) {
58
- references.push({
59
- ...sourceSyncBlockData,
60
- onSameDocument: Boolean(sourceSyncBlockData === null || sourceSyncBlockData === void 0 ? void 0 : sourceSyncBlockData.onSameDocument),
61
- hasAccess: true,
62
- isSource: true
63
- });
64
- }
65
- const unregisteredReferenceData = await this.referenceSyncBlockStoreManager.fetchSyncBlockSourceInfo(referenceResourceId);
66
- if (unregisteredReferenceData) {
67
- references.push({
68
- ...unregisteredReferenceData,
69
- onSameDocument: true,
70
- hasAccess: true,
71
- isSource: false
72
- });
73
- }
74
- (_this$fetchReferences3 = this.fetchReferencesExperience) === null || _this$fetchReferences3 === void 0 ? void 0 : _this$fetchReferences3.success();
75
- return {
76
- references
77
- };
78
- }
79
-
80
- // No remote or local reference exists — show info text with link to doco on how to use Synced Blocks
81
- (_this$fetchReferences4 = this.fetchReferencesExperience) === null || _this$fetchReferences4 === void 0 ? void 0 : _this$fetchReferences4.success();
82
- return {
83
- references: []
84
- };
85
- }
86
- if (!isSourceSyncBlock) {
87
- var _this$fetchReferences6;
88
- // Though no references registered yet for this reference sync block,
89
- // still show the source and the current page itself since they are known
90
- // but not saved yet.
91
- const references = [];
92
- const sourceSyncBlockData = await this.referenceSyncBlockStoreManager.fetchSyncBlockSourceInfo(resourceId);
93
- if (sourceSyncBlockData) {
94
- references.push({
95
- ...sourceSyncBlockData,
96
- onSameDocument: Boolean(sourceSyncBlockData === null || sourceSyncBlockData === void 0 ? void 0 : sourceSyncBlockData.onSameDocument),
97
- hasAccess: true,
98
- isSource: true
99
- });
100
- }
101
- const currentPageData = await this.referenceSyncBlockStoreManager.fetchSyncBlockSourceInfoByLocalId(blockInstanceId);
102
- if (currentPageData) {
103
- references.push({
104
- ...currentPageData,
105
- onSameDocument: true,
106
- hasAccess: true,
107
- isSource: false
108
- });
109
- }
110
- if (references.length === 0) {
111
- var _this$fetchReferences5;
112
- (_this$fetchReferences5 = this.fetchReferencesExperience) === null || _this$fetchReferences5 === void 0 ? void 0 : _this$fetchReferences5.failure({
113
- reason: 'No references found for reference synced block'
114
- });
115
- return {
116
- error: SyncBlockError.Errored
117
- };
118
- }
119
- (_this$fetchReferences6 = this.fetchReferencesExperience) === null || _this$fetchReferences6 === void 0 ? void 0 : _this$fetchReferences6.success();
120
- return {
121
- references
122
- };
123
- }
44
+ return this.getUnregisteredReferences(resourceId, blockInstanceId, isSourceSyncBlock);
124
45
  } else {
125
46
  // No reference found
126
47
  if (isSourceSyncBlock) {
127
- var _this$fetchReferences7;
128
- (_this$fetchReferences7 = this.fetchReferencesExperience) === null || _this$fetchReferences7 === void 0 ? void 0 : _this$fetchReferences7.success();
48
+ var _this$fetchReferences3;
49
+ (_this$fetchReferences3 = this.fetchReferencesExperience) === null || _this$fetchReferences3 === void 0 ? void 0 : _this$fetchReferences3.success();
129
50
  } else {
130
- var _this$fetchReferences8;
131
- (_this$fetchReferences8 = this.fetchReferencesExperience) === null || _this$fetchReferences8 === void 0 ? void 0 : _this$fetchReferences8.failure({
51
+ var _this$fetchReferences4;
52
+ (_this$fetchReferences4 = this.fetchReferencesExperience) === null || _this$fetchReferences4 === void 0 ? void 0 : _this$fetchReferences4.failure({
132
53
  reason: 'No references found for reference synced block'
133
54
  });
134
55
  }
@@ -139,7 +60,7 @@ export class SyncBlockStoreManager {
139
60
  };
140
61
  }
141
62
  }
142
- (_this$fetchReferences9 = this.fetchReferencesExperience) === null || _this$fetchReferences9 === void 0 ? void 0 : _this$fetchReferences9.success();
63
+ (_this$fetchReferences5 = this.fetchReferencesExperience) === null || _this$fetchReferences5 === void 0 ? void 0 : _this$fetchReferences5.success();
143
64
  const sourceInfoPromises = ((_response$references2 = response.references) !== null && _response$references2 !== void 0 ? _response$references2 : []).map(async reference => {
144
65
  var _this$fetchSourceInfo, _this$dataProvider, _this$fetchSourceInfo3;
145
66
  (_this$fetchSourceInfo = this.fetchSourceInfoExperience) === null || _this$fetchSourceInfo === void 0 ? void 0 : _this$fetchSourceInfo.start();
@@ -198,16 +119,95 @@ export class SyncBlockStoreManager {
198
119
  return this.sourceSyncBlockStoreManager;
199
120
  }
200
121
  destroy() {
201
- var _this$fetchReferences0, _this$fetchSourceInfo4;
122
+ var _this$fetchReferences6, _this$fetchSourceInfo4;
202
123
  this.referenceSyncBlockStoreManager.destroy();
203
124
  this.sourceSyncBlockStoreManager.destroy();
204
- (_this$fetchReferences0 = this.fetchReferencesExperience) === null || _this$fetchReferences0 === void 0 ? void 0 : _this$fetchReferences0.abort({
125
+ (_this$fetchReferences6 = this.fetchReferencesExperience) === null || _this$fetchReferences6 === void 0 ? void 0 : _this$fetchReferences6.abort({
205
126
  reason: 'editorDestroyed'
206
127
  });
207
128
  (_this$fetchSourceInfo4 = this.fetchSourceInfoExperience) === null || _this$fetchSourceInfo4 === void 0 ? void 0 : _this$fetchSourceInfo4.abort({
208
129
  reason: 'editorDestroyed'
209
130
  });
210
131
  }
132
+ async getUnregisteredReferences(resourceId, blockInstanceId, isSourceSyncBlock) {
133
+ var _this$fetchReferences0;
134
+ // No reference found
135
+ if (isSourceSyncBlock) {
136
+ var _this$fetchReferences8;
137
+ // Verify that a reference sync block for this specific source actually
138
+ // exists on the current page by checking if the reference manager has
139
+ // an active subscription for the derived reference resourceId.
140
+ const referenceResourceId = this.referenceSyncBlockStoreManager.generateResourceIdForReference(resourceId);
141
+ const hasUnregisteredReferenceOnPage = this.referenceSyncBlockStoreManager.getSubscribedResourceIds().includes(referenceResourceId);
142
+ if (hasUnregisteredReferenceOnPage) {
143
+ var _this$fetchReferences7;
144
+ // This is current page data. It is the same for data for source and reference
145
+ const sourceSyncBlockData = await this.sourceSyncBlockStoreManager.getSyncBlockSourceInfo(blockInstanceId);
146
+ const references = [];
147
+ if (sourceSyncBlockData) {
148
+ const sourceSyncBlockReference = {
149
+ ...sourceSyncBlockData,
150
+ onSameDocument: true,
151
+ hasAccess: true,
152
+ isSource: true
153
+ };
154
+ const referenceSyncBlockReference = {
155
+ ...sourceSyncBlockData,
156
+ onSameDocument: true,
157
+ hasAccess: true,
158
+ isSource: false
159
+ };
160
+ references.push(sourceSyncBlockReference, referenceSyncBlockReference);
161
+ }
162
+ (_this$fetchReferences7 = this.fetchReferencesExperience) === null || _this$fetchReferences7 === void 0 ? void 0 : _this$fetchReferences7.success();
163
+ return {
164
+ references
165
+ };
166
+ }
167
+
168
+ // No remote or local reference exists — show info text with link to doco on how to use Synced Blocks
169
+ (_this$fetchReferences8 = this.fetchReferencesExperience) === null || _this$fetchReferences8 === void 0 ? void 0 : _this$fetchReferences8.success();
170
+ return {
171
+ references: []
172
+ };
173
+ }
174
+
175
+ // Though no references registered yet for this reference sync block,
176
+ // still show the source and the current page itself since they are known
177
+ // but not saved yet.
178
+ const references = [];
179
+ const sourceSyncBlockData = await this.referenceSyncBlockStoreManager.fetchSyncBlockSourceInfo(resourceId);
180
+ if (sourceSyncBlockData) {
181
+ references.push({
182
+ ...sourceSyncBlockData,
183
+ onSameDocument: Boolean(sourceSyncBlockData === null || sourceSyncBlockData === void 0 ? void 0 : sourceSyncBlockData.onSameDocument),
184
+ hasAccess: true,
185
+ isSource: true
186
+ });
187
+ }
188
+ const currentPageData = await this.referenceSyncBlockStoreManager.fetchSyncBlockSourceInfoByLocalId(blockInstanceId);
189
+ if (currentPageData) {
190
+ references.push({
191
+ ...currentPageData,
192
+ onSameDocument: true,
193
+ hasAccess: true,
194
+ isSource: false
195
+ });
196
+ }
197
+ if (references.length === 0) {
198
+ var _this$fetchReferences9;
199
+ (_this$fetchReferences9 = this.fetchReferencesExperience) === null || _this$fetchReferences9 === void 0 ? void 0 : _this$fetchReferences9.failure({
200
+ reason: 'No references found for reference synced block'
201
+ });
202
+ return {
203
+ error: SyncBlockError.Errored
204
+ };
205
+ }
206
+ (_this$fetchReferences0 = this.fetchReferencesExperience) === null || _this$fetchReferences0 === void 0 ? void 0 : _this$fetchReferences0.success();
207
+ return {
208
+ references
209
+ };
210
+ }
211
211
  }
212
212
  const createSyncBlockStoreManager = dataProvider => {
213
213
  return new SyncBlockStoreManager(dataProvider);
@@ -11,6 +11,7 @@ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t =
11
11
  import _regeneratorRuntime from "@babel/runtime/regenerator";
12
12
  import isEqual from 'lodash/isEqual';
13
13
  import { logException } from '@atlaskit/editor-common/monitoring';
14
+ import { fg } from '@atlaskit/platform-feature-flags';
14
15
  import { SyncBlockError } from '../common/types';
15
16
  import { fetchErrorPayload, fetchSuccessPayload, getSourceInfoErrorPayload, updateReferenceErrorPayload } from '../utils/errorHandling';
16
17
  import { getFetchExperience, getFetchSourceInfoExperience, getSaveReferenceExperience } from '../utils/experienceTracking';
@@ -30,7 +31,7 @@ var CACHE_KEY_PREFIX = 'sync-block-data-';
30
31
  export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
31
32
  // Track the setTimeout handle for queued flush so we can cancel it on destroy
32
33
 
33
- function ReferenceSyncBlockStoreManager(dataProvider) {
34
+ function ReferenceSyncBlockStoreManager(dataProvider, viewMode) {
34
35
  var _this = this,
35
36
  _this$dataProvider;
36
37
  _classCallCheck(this, ReferenceSyncBlockStoreManager);
@@ -45,6 +46,7 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
45
46
  // Track if another flush is needed after the current one completes
46
47
  _defineProperty(this, "flushNeededAfterCurrent", false);
47
48
  this.dataProvider = dataProvider;
49
+ this.viewMode = viewMode;
48
50
  this.syncBlockFetchDataRequests = new Map();
49
51
  this.syncBlockSourceInfoRequests = new Map();
50
52
  this.newlyAddedSyncBlocks = new Set();
@@ -695,14 +697,20 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
695
697
  return _regeneratorRuntime.wrap(function _callee3$(_context4) {
696
698
  while (1) switch (_context4.prev = _context4.next) {
697
699
  case 0:
698
- if (this.isCacheDirty) {
700
+ if (!(this.viewMode === 'view' && fg('platform_synced_block_patch_8'))) {
699
701
  _context4.next = 2;
700
702
  break;
701
703
  }
702
- return _context4.abrupt("return", true);
704
+ return _context4.abrupt("return", false);
703
705
  case 2:
706
+ if (this.isCacheDirty) {
707
+ _context4.next = 4;
708
+ break;
709
+ }
710
+ return _context4.abrupt("return", true);
711
+ case 4:
704
712
  if (!this.isFlushInProgress) {
705
- _context4.next = 7;
713
+ _context4.next = 9;
706
714
  break;
707
715
  }
708
716
  // Mark that another flush is needed after the current one completes
@@ -710,22 +718,22 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
710
718
 
711
719
  // We return true here because we know the pending flush will handle the dirty cache
712
720
  return _context4.abrupt("return", true);
713
- case 7:
721
+ case 9:
714
722
  this.isFlushInProgress = true;
715
- case 8:
723
+ case 10:
716
724
  success = true; // a copy of the subscriptions STRUCTURE (without the callbacks)
717
725
  // To be saved as the last flushed structure if the flush is successful
718
726
  syncedBlocksToFlush = {};
719
- _context4.prev = 10;
727
+ _context4.prev = 12;
720
728
  if (this.dataProvider) {
721
- _context4.next = 13;
729
+ _context4.next = 15;
722
730
  break;
723
731
  }
724
732
  throw new Error('Data provider not set');
725
- case 13:
733
+ case 15:
726
734
  blocks = []; // First, build the complete subscription structure
727
735
  _iterator = _createForOfIteratorHelper(this._subscriptionManager.getSubscriptions().entries());
728
- _context4.prev = 15;
736
+ _context4.prev = 17;
729
737
  _loop = /*#__PURE__*/_regeneratorRuntime.mark(function _loop() {
730
738
  var _step$value, resourceId, callbacks;
731
739
  return _regeneratorRuntime.wrap(function _loop$(_context3) {
@@ -747,34 +755,34 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
747
755
  }, _loop);
748
756
  });
749
757
  _iterator.s();
750
- case 18:
758
+ case 20:
751
759
  if ((_step = _iterator.n()).done) {
752
- _context4.next = 22;
760
+ _context4.next = 24;
753
761
  break;
754
762
  }
755
- return _context4.delegateYield(_loop(), "t0", 20);
756
- case 20:
757
- _context4.next = 18;
758
- break;
763
+ return _context4.delegateYield(_loop(), "t0", 22);
759
764
  case 22:
760
- _context4.next = 27;
765
+ _context4.next = 20;
761
766
  break;
762
767
  case 24:
763
- _context4.prev = 24;
764
- _context4.t1 = _context4["catch"](15);
768
+ _context4.next = 29;
769
+ break;
770
+ case 26:
771
+ _context4.prev = 26;
772
+ _context4.t1 = _context4["catch"](17);
765
773
  _iterator.e(_context4.t1);
766
- case 27:
767
- _context4.prev = 27;
774
+ case 29:
775
+ _context4.prev = 29;
768
776
  _iterator.f();
769
- return _context4.finish(27);
770
- case 30:
777
+ return _context4.finish(29);
778
+ case 32:
771
779
  if (!isEqual(syncedBlocksToFlush, this.lastFlushedSyncedBlocks)) {
772
- _context4.next = 33;
780
+ _context4.next = 35;
773
781
  break;
774
782
  }
775
783
  this.isCacheDirty = false; // Reset since we're considering this a successful no-op flush
776
784
  return _context4.abrupt("return", true);
777
- case 33:
785
+ case 35:
778
786
  // reset isCacheDirty early to prevent race condition
779
787
  // There is a race condition where if a user makes changes (create/delete) to a reference sync block
780
788
  // on a live page and the reference sync block is being saved while the user
@@ -782,9 +790,9 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
782
790
  // exactly at a time when the updateReferenceData is being executed asynchronously.
783
791
  this.isCacheDirty = false;
784
792
  (_this$saveExperience = this.saveExperience) === null || _this$saveExperience === void 0 || _this$saveExperience.start();
785
- _context4.next = 37;
793
+ _context4.next = 39;
786
794
  return this.dataProvider.updateReferenceData(blocks);
787
- case 37:
795
+ case 39:
788
796
  updateResult = _context4.sent;
789
797
  if (!updateResult.success) {
790
798
  success = false;
@@ -793,11 +801,11 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
793
801
  });
794
802
  (_this$fireAnalyticsEv6 = this.fireAnalyticsEvent) === null || _this$fireAnalyticsEv6 === void 0 || _this$fireAnalyticsEv6.call(this, updateReferenceErrorPayload(updateResult.error || 'Failed to update reference synced blocks on the document'));
795
803
  }
796
- _context4.next = 47;
804
+ _context4.next = 49;
797
805
  break;
798
- case 41:
799
- _context4.prev = 41;
800
- _context4.t2 = _context4["catch"](10);
806
+ case 43:
807
+ _context4.prev = 43;
808
+ _context4.t2 = _context4["catch"](12);
801
809
  success = false;
802
810
  logException(_context4.t2, {
803
811
  location: 'editor-synced-block-provider/referenceSyncBlockStoreManager'
@@ -806,8 +814,8 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
806
814
  reason: _context4.t2.message
807
815
  });
808
816
  (_this$fireAnalyticsEv7 = this.fireAnalyticsEvent) === null || _this$fireAnalyticsEv7 === void 0 || _this$fireAnalyticsEv7.call(this, updateReferenceErrorPayload(_context4.t2.message));
809
- case 47:
810
- _context4.prev = 47;
817
+ case 49:
818
+ _context4.prev = 49;
811
819
  if (!success) {
812
820
  // set isCacheDirty back to true for cases where it failed to update the reference synced blocks on the BE
813
821
  this.isCacheDirty = true;
@@ -829,14 +837,14 @@ export var ReferenceSyncBlockStoreManager = /*#__PURE__*/function () {
829
837
  void _this7.flush();
830
838
  }, 0);
831
839
  }
832
- return _context4.finish(47);
833
- case 52:
840
+ return _context4.finish(49);
841
+ case 54:
834
842
  return _context4.abrupt("return", success);
835
- case 53:
843
+ case 55:
836
844
  case "end":
837
845
  return _context4.stop();
838
846
  }
839
- }, _callee3, this, [[10, 41, 47, 52], [15, 24, 27, 30]]);
847
+ }, _callee3, this, [[12, 43, 49, 54], [17, 26, 29, 32]]);
840
848
  }));
841
849
  function flush() {
842
850
  return _flush.apply(this, arguments);