@atlaskit/editor-plugin-show-diff 14.1.0 → 14.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +9 -0
- package/dist/cjs/pm-plugins/calculateDiff/calculateDiffDecorations.js +78 -41
- package/dist/cjs/pm-plugins/decorations/utils/getAttrChangeRanges.js +59 -30
- package/dist/es2019/pm-plugins/calculateDiff/calculateDiffDecorations.js +40 -3
- package/dist/es2019/pm-plugins/decorations/utils/getAttrChangeRanges.js +55 -30
- package/dist/esm/pm-plugins/calculateDiff/calculateDiffDecorations.js +78 -41
- package/dist/esm/pm-plugins/decorations/utils/getAttrChangeRanges.js +59 -30
- package/dist/types/pm-plugins/decorations/utils/getAttrChangeRanges.d.ts +12 -2
- package/package.json +8 -5
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,14 @@
|
|
|
1
1
|
# @atlaskit/editor-plugin-show-diff
|
|
2
2
|
|
|
3
|
+
## 14.1.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [`b1510eccd9729`](https://bitbucket.org/atlassian/atlassian-frontend-monorepo/commits/b1510eccd9729) -
|
|
8
|
+
Reduce false-positive attribute diff decorations behind
|
|
9
|
+
`platform_editor_reduce_diff_attr_sensitivity`.
|
|
10
|
+
- Updated dependencies
|
|
11
|
+
|
|
3
12
|
## 14.1.0
|
|
4
13
|
|
|
5
14
|
### Minor Changes
|
|
@@ -13,6 +13,7 @@ var _memoizeOne = _interopRequireDefault(require("memoize-one"));
|
|
|
13
13
|
var _prosemirrorChangeset = require("prosemirror-changeset");
|
|
14
14
|
var _deprecatedPlatformFeatureExperiments = require("@atlaskit/editor-common/deprecated-platform-feature-experiments");
|
|
15
15
|
var _document = require("@atlaskit/editor-common/utils/document");
|
|
16
|
+
var _transform = require("@atlaskit/editor-prosemirror/transform");
|
|
16
17
|
var _view = require("@atlaskit/editor-prosemirror/view");
|
|
17
18
|
var _fg = require("@atlaskit/platform-feature-flags/fg");
|
|
18
19
|
var _expValEquals = require("@atlaskit/tmp-editor-statsig/exp-val-equals");
|
|
@@ -294,7 +295,7 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
294
295
|
} else {
|
|
295
296
|
simplifiedSteps = (0, _simplifySteps.simplifySteps)(steps, originalDoc);
|
|
296
297
|
}
|
|
297
|
-
var
|
|
298
|
+
var pendingAttrSteps = [];
|
|
298
299
|
var stepMaps = [];
|
|
299
300
|
var _iterator = _createForOfIteratorHelper(simplifiedSteps),
|
|
300
301
|
_step;
|
|
@@ -304,20 +305,56 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
304
305
|
var result = step.apply(steppedDoc);
|
|
305
306
|
if (result.failed === null && result.doc) {
|
|
306
307
|
if ((0, _getAttrChangeRanges.stepIsValidAttrChange)(step, steppedDoc, result.doc)) {
|
|
307
|
-
|
|
308
|
+
pendingAttrSteps.push({
|
|
309
|
+
afterNode: result.doc.nodeAt(step.pos),
|
|
310
|
+
beforeNode: steppedDoc.nodeAt(step.pos),
|
|
311
|
+
mapIndex: stepMaps.length,
|
|
312
|
+
step: step
|
|
313
|
+
});
|
|
308
314
|
}
|
|
309
315
|
stepMaps.push(step.getMap());
|
|
310
316
|
steppedDoc = result.doc;
|
|
311
317
|
}
|
|
312
318
|
}
|
|
313
|
-
|
|
314
|
-
//
|
|
315
|
-
// changes and ignores differences in attributes which don't affect decoration positions
|
|
319
|
+
// Gate the complete attribution fix: mapped positions and step-time nodes are used together.
|
|
320
|
+
// The fallback deliberately preserves the legacy raw-position lookups for rollout safety.
|
|
316
321
|
} catch (err) {
|
|
317
322
|
_iterator.e(err);
|
|
318
323
|
} finally {
|
|
319
324
|
_iterator.f();
|
|
320
325
|
}
|
|
326
|
+
var attrStepContexts = (0, _fg.fg)('platform_editor_reduce_diff_attr_sensitivity') ? pendingAttrSteps.flatMap(function (_ref0) {
|
|
327
|
+
var afterNode = _ref0.afterNode,
|
|
328
|
+
beforeNode = _ref0.beforeNode,
|
|
329
|
+
mapIndex = _ref0.mapIndex,
|
|
330
|
+
step = _ref0.step;
|
|
331
|
+
var finalPosition = new _transform.Mapping(stepMaps.slice(mapIndex + 1)).mapResult(step.pos);
|
|
332
|
+
if (finalPosition.deleted) {
|
|
333
|
+
return [];
|
|
334
|
+
}
|
|
335
|
+
var originalPosition = new _transform.Mapping(stepMaps.slice(0, mapIndex)).invert().mapResult(step.pos);
|
|
336
|
+
return [_objectSpread(_objectSpread({
|
|
337
|
+
afterNode: afterNode,
|
|
338
|
+
beforeNode: beforeNode,
|
|
339
|
+
finalPos: finalPosition.pos
|
|
340
|
+
}, originalPosition.deleted ? {} : {
|
|
341
|
+
originalPos: originalPosition.pos
|
|
342
|
+
}), {}, {
|
|
343
|
+
step: step
|
|
344
|
+
})];
|
|
345
|
+
}) : pendingAttrSteps.map(function (_ref1) {
|
|
346
|
+
var step = _ref1.step;
|
|
347
|
+
return {
|
|
348
|
+
afterNode: tr.doc.nodeAt(step.pos),
|
|
349
|
+
beforeNode: originalDoc.nodeAt(step.pos),
|
|
350
|
+
finalPos: step.pos,
|
|
351
|
+
originalPos: step.pos,
|
|
352
|
+
step: step
|
|
353
|
+
};
|
|
354
|
+
});
|
|
355
|
+
|
|
356
|
+
// Rather than using .eq() we use a custom function that only checks for structural
|
|
357
|
+
// changes and ignores differences in attributes which don't affect decoration positions
|
|
321
358
|
if (!(0, _document.areNodesEqualIgnoreAttrs)(steppedDoc, tr.doc)) {
|
|
322
359
|
var _api$analytics;
|
|
323
360
|
var recoveredViaContentEquality = (0, _areDocsEqualByBlockStructureAndText.areDocsEqualByBlockStructureAndText)(steppedDoc, tr.doc);
|
|
@@ -531,7 +568,7 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
531
568
|
isInserted: true
|
|
532
569
|
})));
|
|
533
570
|
});
|
|
534
|
-
(0, _getAttrChangeRanges.getAttrChangeRanges)(tr.doc,
|
|
571
|
+
(0, _getAttrChangeRanges.getAttrChangeRanges)(tr.doc, attrStepContexts, originalDoc).forEach(function (change) {
|
|
535
572
|
if (change.isInline) {
|
|
536
573
|
// Inline nodes (e.g. date, emoji, mention, status) need an inline decoration rather than a block decoration
|
|
537
574
|
var isActive = activeIndexPos && change.fromB === activeIndexPos.from && change.toB === activeIndexPos.to;
|
|
@@ -621,42 +658,42 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
621
658
|
};
|
|
622
659
|
var calculateDiffDecorations = exports.calculateDiffDecorations = (0, _memoizeOne.default)(calculateDiffDecorationsInner,
|
|
623
660
|
// Cache results unless relevant inputs change
|
|
624
|
-
function (
|
|
625
|
-
var
|
|
626
|
-
var
|
|
627
|
-
|
|
628
|
-
pluginState =
|
|
629
|
-
state =
|
|
630
|
-
colorScheme =
|
|
631
|
-
intl =
|
|
632
|
-
activeIndexPos =
|
|
633
|
-
isInverted =
|
|
634
|
-
diffType =
|
|
635
|
-
hideDeletedDiffs =
|
|
636
|
-
hideAddedDiffsUnderline =
|
|
637
|
-
showIndicators =
|
|
638
|
-
smartThresholds =
|
|
639
|
-
deletedDiffPlacement =
|
|
640
|
-
inlineDeletedDiffPlacement =
|
|
641
|
-
var
|
|
642
|
-
|
|
643
|
-
lastPluginState =
|
|
644
|
-
lastState =
|
|
645
|
-
lastColorScheme =
|
|
646
|
-
lastIntl =
|
|
647
|
-
lastActiveIndexPos =
|
|
648
|
-
lastIsInverted =
|
|
649
|
-
lastDiffType =
|
|
650
|
-
lastHideDeletedDiffs =
|
|
651
|
-
lastHideAddedDiffsUnderline =
|
|
652
|
-
lastShowIndicators =
|
|
653
|
-
lastSmartThresholds =
|
|
654
|
-
lastDeletedDiffPlacement =
|
|
655
|
-
lastInlineDeletedDiffPlacement =
|
|
661
|
+
function (_ref10, _ref11) {
|
|
662
|
+
var _ref15;
|
|
663
|
+
var _ref12 = (0, _slicedToArray2.default)(_ref10, 1),
|
|
664
|
+
_ref12$ = _ref12[0],
|
|
665
|
+
pluginState = _ref12$.pluginState,
|
|
666
|
+
state = _ref12$.state,
|
|
667
|
+
colorScheme = _ref12$.colorScheme,
|
|
668
|
+
intl = _ref12$.intl,
|
|
669
|
+
activeIndexPos = _ref12$.activeIndexPos,
|
|
670
|
+
isInverted = _ref12$.isInverted,
|
|
671
|
+
diffType = _ref12$.diffType,
|
|
672
|
+
hideDeletedDiffs = _ref12$.hideDeletedDiffs,
|
|
673
|
+
hideAddedDiffsUnderline = _ref12$.hideAddedDiffsUnderline,
|
|
674
|
+
showIndicators = _ref12$.showIndicators,
|
|
675
|
+
smartThresholds = _ref12$.smartThresholds,
|
|
676
|
+
deletedDiffPlacement = _ref12$.deletedDiffPlacement,
|
|
677
|
+
inlineDeletedDiffPlacement = _ref12$.inlineDeletedDiffPlacement;
|
|
678
|
+
var _ref13 = (0, _slicedToArray2.default)(_ref11, 1),
|
|
679
|
+
_ref13$ = _ref13[0],
|
|
680
|
+
lastPluginState = _ref13$.pluginState,
|
|
681
|
+
lastState = _ref13$.state,
|
|
682
|
+
lastColorScheme = _ref13$.colorScheme,
|
|
683
|
+
lastIntl = _ref13$.intl,
|
|
684
|
+
lastActiveIndexPos = _ref13$.activeIndexPos,
|
|
685
|
+
lastIsInverted = _ref13$.isInverted,
|
|
686
|
+
lastDiffType = _ref13$.diffType,
|
|
687
|
+
lastHideDeletedDiffs = _ref13$.hideDeletedDiffs,
|
|
688
|
+
lastHideAddedDiffsUnderline = _ref13$.hideAddedDiffsUnderline,
|
|
689
|
+
lastShowIndicators = _ref13$.showIndicators,
|
|
690
|
+
lastSmartThresholds = _ref13$.smartThresholds,
|
|
691
|
+
lastDeletedDiffPlacement = _ref13$.deletedDiffPlacement,
|
|
692
|
+
lastInlineDeletedDiffPlacement = _ref13$.inlineDeletedDiffPlacement;
|
|
656
693
|
var originalDocIsSame = lastPluginState.originalDoc && pluginState.originalDoc && pluginState.originalDoc.eq(lastPluginState.originalDoc);
|
|
657
694
|
if ((0, _isExtendedEnabled.isExtendedEnabled)(diffType)) {
|
|
658
|
-
var
|
|
659
|
-
return (
|
|
695
|
+
var _ref14;
|
|
696
|
+
return (_ref14 = colorScheme === lastColorScheme && intl.locale === lastIntl.locale && isInverted === lastIsInverted && diffType === lastDiffType && (0, _isEqual.default)(activeIndexPos, lastActiveIndexPos) && originalDocIsSame && (0, _isEqual.default)(pluginState.steps, lastPluginState.steps) && (0, _isEqual.default)(pluginState.stepAttributions, lastPluginState.stepAttributions) && state.doc.eq(lastState.doc) && hideDeletedDiffs === lastHideDeletedDiffs && hideAddedDiffsUnderline === lastHideAddedDiffsUnderline && showIndicators === lastShowIndicators && (0, _isEqual.default)(smartThresholds, lastSmartThresholds) && deletedDiffPlacement === lastDeletedDiffPlacement && inlineDeletedDiffPlacement === lastInlineDeletedDiffPlacement) !== null && _ref14 !== void 0 ? _ref14 : false;
|
|
660
697
|
}
|
|
661
|
-
return (
|
|
698
|
+
return (_ref15 = originalDocIsSame && (0, _isEqual.default)(pluginState.steps, lastPluginState.steps) && (0, _isEqual.default)(pluginState.stepAttributions, lastPluginState.stepAttributions) && state.doc.eq(lastState.doc) && colorScheme === lastColorScheme && intl.locale === lastIntl.locale && (0, _isEqual.default)(activeIndexPos, lastActiveIndexPos) && hideDeletedDiffs === lastHideDeletedDiffs) !== null && _ref15 !== void 0 ? _ref15 : false;
|
|
662
699
|
});
|
|
@@ -6,10 +6,13 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
6
6
|
});
|
|
7
7
|
exports.stepIsValidAttrChange = exports.getAttrChangeRanges = void 0;
|
|
8
8
|
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
|
|
9
|
+
var _isEqual = _interopRequireDefault(require("lodash/isEqual"));
|
|
10
|
+
var _omit = _interopRequireDefault(require("lodash/omit"));
|
|
9
11
|
var _steps = require("@atlaskit/adf-schema/steps");
|
|
10
12
|
var _deprecatedPlatformFeatureExperiments = require("@atlaskit/editor-common/deprecated-platform-feature-experiments");
|
|
11
13
|
var _nodeTypeUtils = require("@atlaskit/editor-common/utils/node-type-utils");
|
|
12
14
|
var _transform = require("@atlaskit/editor-prosemirror/transform");
|
|
15
|
+
var _fg = require("@atlaskit/platform-feature-flags/fg");
|
|
13
16
|
var _expValEquals = require("@atlaskit/tmp-editor-statsig/exp-val-equals");
|
|
14
17
|
var _diffableAttrs = require("./diffableAttrs");
|
|
15
18
|
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
@@ -41,33 +44,57 @@ var isInlineAttrChangeNodeName = function isInlineAttrChangeNodeName(nodeName) {
|
|
|
41
44
|
// Extension node type names. Their "any attr except localId" exclude rule lives
|
|
42
45
|
// in the shared `diffableAttrs` map and is applied via `isDiffableAttr` below.
|
|
43
46
|
var extensionNodeNames = ['extension', 'inlineExtension', 'bodiedExtension'];
|
|
47
|
+
var transientExtensionAttrPaths = ['localId', 'parameters.macroParams._parentId'];
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Removes extension metadata that can change between document versions without changing the
|
|
51
|
+
* extension's user-visible configuration.
|
|
52
|
+
*/
|
|
53
|
+
var getComparableExtensionAttrs = function getComparableExtensionAttrs(node) {
|
|
54
|
+
return (0, _omit.default)(node.attrs, transientExtensionAttrPaths);
|
|
55
|
+
};
|
|
56
|
+
var haveSameRelevantExtensionAttrs = function haveSameRelevantExtensionAttrs(beforeNode, afterNode) {
|
|
57
|
+
return (0, _isEqual.default)(getComparableExtensionAttrs(beforeNode), getComparableExtensionAttrs(afterNode));
|
|
58
|
+
};
|
|
44
59
|
var getStepAttrs = function getStepAttrs(step) {
|
|
45
60
|
if (step instanceof _transform.AttrStep) {
|
|
46
61
|
return [step.attr];
|
|
47
62
|
}
|
|
48
|
-
if (step
|
|
63
|
+
if (step.attrs) {
|
|
49
64
|
return Object.keys(step.attrs);
|
|
50
65
|
}
|
|
51
66
|
return [];
|
|
52
67
|
};
|
|
53
|
-
var getAttrChangeRanges = exports.getAttrChangeRanges = function getAttrChangeRanges(doc,
|
|
54
|
-
return
|
|
68
|
+
var getAttrChangeRanges = exports.getAttrChangeRanges = function getAttrChangeRanges(doc, attrStepContexts, originalDoc) {
|
|
69
|
+
return attrStepContexts.map(function (attrStepContext) {
|
|
70
|
+
var afterNode = attrStepContext.afterNode,
|
|
71
|
+
beforeNode = attrStepContext.beforeNode,
|
|
72
|
+
finalPos = attrStepContext.finalPos,
|
|
73
|
+
originalPos = attrStepContext.originalPos,
|
|
74
|
+
step = attrStepContext.step;
|
|
55
75
|
if (!(step instanceof _transform.AttrStep) && !(step instanceof _steps.SetAttrsStep)) {
|
|
56
76
|
return undefined;
|
|
57
77
|
}
|
|
58
78
|
var stepAttrs = getStepAttrs(step);
|
|
59
|
-
|
|
60
|
-
|
|
79
|
+
// SetAttrsStep contains the complete replacement attrs, not only the attrs that changed.
|
|
80
|
+
// Keep the legacy payload-based checks until the rollout gate is enabled, and fall back
|
|
81
|
+
// to them if either step-time node is unavailable.
|
|
82
|
+
var attrsToCheck = (0, _fg.fg)('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode ? stepAttrs.filter(function (attrName) {
|
|
83
|
+
return !(0, _isEqual.default)(beforeNode.attrs[attrName], afterNode.attrs[attrName]);
|
|
84
|
+
}) : stepAttrs;
|
|
85
|
+
var $pos = doc.resolve(finalPos);
|
|
86
|
+
var nodeAtPos = doc.nodeAt(finalPos);
|
|
87
|
+
var originalNodeAtPos = originalPos === undefined ? null : originalDoc.nodeAt(originalPos);
|
|
61
88
|
|
|
62
89
|
// date node: timestamp attribute change — highlight the date node itself (inline)
|
|
63
|
-
if (
|
|
90
|
+
if (attrsToCheck.some(function (v) {
|
|
64
91
|
return dateAttrs.includes(v);
|
|
65
92
|
}) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'date' && !(0, _deprecatedPlatformFeatureExperiments.isExperimentEnabled)('platform_editor_improve_inline_diffs', function () {
|
|
66
93
|
return (0, _expValEquals.expValEquals)('platform_editor_improve_inline_diffs', 'isEnabled', true);
|
|
67
94
|
})) {
|
|
68
95
|
return {
|
|
69
|
-
fromB:
|
|
70
|
-
toB:
|
|
96
|
+
fromB: finalPos,
|
|
97
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
71
98
|
isInline: true,
|
|
72
99
|
inlineNodeName: 'date'
|
|
73
100
|
};
|
|
@@ -82,30 +109,29 @@ var getAttrChangeRanges = exports.getAttrChangeRanges = function getAttrChangeRa
|
|
|
82
109
|
var nodeName = nodeAtPos.type.name;
|
|
83
110
|
if (isInlineAttrChangeNodeName(nodeName)) {
|
|
84
111
|
var watchedAttrs = inlineNodeAttrMap[nodeName];
|
|
85
|
-
if (
|
|
112
|
+
if (attrsToCheck.some(function (v) {
|
|
86
113
|
return watchedAttrs.includes(v);
|
|
87
114
|
})) {
|
|
88
|
-
var originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
89
115
|
return _objectSpread({
|
|
90
|
-
fromB:
|
|
91
|
-
toB:
|
|
116
|
+
fromB: finalPos,
|
|
117
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
92
118
|
isInline: true,
|
|
93
119
|
inlineNodeName: nodeName
|
|
94
|
-
}, originalNodeAtPos && {
|
|
95
|
-
fromA:
|
|
96
|
-
toA:
|
|
120
|
+
}, originalPos !== undefined && originalNodeAtPos && {
|
|
121
|
+
fromA: originalPos,
|
|
122
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
97
123
|
});
|
|
98
124
|
}
|
|
99
125
|
}
|
|
100
126
|
}
|
|
101
127
|
|
|
102
128
|
// taskItem node: state attribute change — highlight the taskItem node
|
|
103
|
-
if (
|
|
129
|
+
if (attrsToCheck.some(function (v) {
|
|
104
130
|
return taskItemAttrs.includes(v);
|
|
105
131
|
}) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'taskItem') {
|
|
106
132
|
return {
|
|
107
|
-
fromB:
|
|
108
|
-
toB:
|
|
133
|
+
fromB: finalPos,
|
|
134
|
+
toB: finalPos + nodeAtPos.nodeSize
|
|
109
135
|
};
|
|
110
136
|
}
|
|
111
137
|
|
|
@@ -113,33 +139,36 @@ var getAttrChangeRanges = exports.getAttrChangeRanges = function getAttrChangeRa
|
|
|
113
139
|
// (e.g. note -> warning) — highlight the new panel and, when the original node
|
|
114
140
|
// is resolvable, expose its range (fromA/toA) so the caller can render the old
|
|
115
141
|
// panel as a "deleted" widget for a before/after comparison.
|
|
116
|
-
if (
|
|
142
|
+
if (attrsToCheck.some(function (v) {
|
|
117
143
|
return panelAttrs.includes(v);
|
|
118
144
|
}) && nodeAtPos && (0, _nodeTypeUtils.getBaseNodeTypeName)(nodeAtPos.type) === 'panel') {
|
|
119
|
-
var _originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
120
145
|
return _objectSpread({
|
|
121
|
-
fromB:
|
|
122
|
-
toB:
|
|
123
|
-
},
|
|
124
|
-
fromA:
|
|
125
|
-
toA:
|
|
146
|
+
fromB: finalPos,
|
|
147
|
+
toB: finalPos + nodeAtPos.nodeSize
|
|
148
|
+
}, originalPos !== undefined && originalNodeAtPos && {
|
|
149
|
+
fromA: originalPos,
|
|
150
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
126
151
|
});
|
|
127
152
|
}
|
|
128
153
|
|
|
129
|
-
//
|
|
130
|
-
|
|
154
|
+
// Extension nodes: highlight changes to user-visible configuration. When enabled,
|
|
155
|
+
// transient extension metadata is ignored by the comparison below.
|
|
156
|
+
if (nodeAtPos && extensionNodeNames.includes(nodeAtPos.type.name) && attrsToCheck.some(function (v) {
|
|
131
157
|
return (0, _diffableAttrs.isDiffableAttr)(nodeAtPos.type.name, v);
|
|
132
158
|
})) {
|
|
159
|
+
if ((0, _fg.fg)('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode && beforeNode.type === afterNode.type && haveSameRelevantExtensionAttrs(beforeNode, afterNode)) {
|
|
160
|
+
return undefined;
|
|
161
|
+
}
|
|
133
162
|
var isInline = nodeAtPos.type.name === 'inlineExtension';
|
|
134
163
|
return {
|
|
135
|
-
fromB:
|
|
136
|
-
toB:
|
|
164
|
+
fromB: finalPos,
|
|
165
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
137
166
|
isInline: isInline
|
|
138
167
|
};
|
|
139
168
|
}
|
|
140
169
|
|
|
141
170
|
// media node: id/collection/url attribute change — highlight the mediaSingle parent
|
|
142
|
-
if (
|
|
171
|
+
if (attrsToCheck.some(function (v) {
|
|
143
172
|
return mediaAttrs.includes(v);
|
|
144
173
|
}) && $pos.parent.type === doc.type.schema.nodes.mediaSingle) {
|
|
145
174
|
var startPos = $pos.pos + $pos.parentOffset;
|
|
@@ -3,6 +3,7 @@ import memoizeOne from 'memoize-one';
|
|
|
3
3
|
import { ChangeSet, simplifyChanges } from 'prosemirror-changeset';
|
|
4
4
|
import { isExperimentEnabled } from '@atlaskit/editor-common/deprecated-platform-feature-experiments';
|
|
5
5
|
import { areNodesEqualIgnoreAttrs } from '@atlaskit/editor-common/utils/document';
|
|
6
|
+
import { Mapping } from '@atlaskit/editor-prosemirror/transform';
|
|
6
7
|
import { DecorationSet } from '@atlaskit/editor-prosemirror/view';
|
|
7
8
|
import { fg } from '@atlaskit/platform-feature-flags/fg';
|
|
8
9
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
@@ -268,18 +269,54 @@ const calculateDiffDecorationsInner = ({
|
|
|
268
269
|
} else {
|
|
269
270
|
simplifiedSteps = simplifySteps(steps, originalDoc);
|
|
270
271
|
}
|
|
271
|
-
const
|
|
272
|
+
const pendingAttrSteps = [];
|
|
272
273
|
const stepMaps = [];
|
|
273
274
|
for (const step of simplifiedSteps) {
|
|
274
275
|
const result = step.apply(steppedDoc);
|
|
275
276
|
if (result.failed === null && result.doc) {
|
|
276
277
|
if (stepIsValidAttrChange(step, steppedDoc, result.doc)) {
|
|
277
|
-
|
|
278
|
+
pendingAttrSteps.push({
|
|
279
|
+
afterNode: result.doc.nodeAt(step.pos),
|
|
280
|
+
beforeNode: steppedDoc.nodeAt(step.pos),
|
|
281
|
+
mapIndex: stepMaps.length,
|
|
282
|
+
step
|
|
283
|
+
});
|
|
278
284
|
}
|
|
279
285
|
stepMaps.push(step.getMap());
|
|
280
286
|
steppedDoc = result.doc;
|
|
281
287
|
}
|
|
282
288
|
}
|
|
289
|
+
// Gate the complete attribution fix: mapped positions and step-time nodes are used together.
|
|
290
|
+
// The fallback deliberately preserves the legacy raw-position lookups for rollout safety.
|
|
291
|
+
const attrStepContexts = fg('platform_editor_reduce_diff_attr_sensitivity') ? pendingAttrSteps.flatMap(({
|
|
292
|
+
afterNode,
|
|
293
|
+
beforeNode,
|
|
294
|
+
mapIndex,
|
|
295
|
+
step
|
|
296
|
+
}) => {
|
|
297
|
+
const finalPosition = new Mapping(stepMaps.slice(mapIndex + 1)).mapResult(step.pos);
|
|
298
|
+
if (finalPosition.deleted) {
|
|
299
|
+
return [];
|
|
300
|
+
}
|
|
301
|
+
const originalPosition = new Mapping(stepMaps.slice(0, mapIndex)).invert().mapResult(step.pos);
|
|
302
|
+
return [{
|
|
303
|
+
afterNode,
|
|
304
|
+
beforeNode,
|
|
305
|
+
finalPos: finalPosition.pos,
|
|
306
|
+
...(originalPosition.deleted ? {} : {
|
|
307
|
+
originalPos: originalPosition.pos
|
|
308
|
+
}),
|
|
309
|
+
step
|
|
310
|
+
}];
|
|
311
|
+
}) : pendingAttrSteps.map(({
|
|
312
|
+
step
|
|
313
|
+
}) => ({
|
|
314
|
+
afterNode: tr.doc.nodeAt(step.pos),
|
|
315
|
+
beforeNode: originalDoc.nodeAt(step.pos),
|
|
316
|
+
finalPos: step.pos,
|
|
317
|
+
originalPos: step.pos,
|
|
318
|
+
step
|
|
319
|
+
}));
|
|
283
320
|
|
|
284
321
|
// Rather than using .eq() we use a custom function that only checks for structural
|
|
285
322
|
// changes and ignores differences in attributes which don't affect decoration positions
|
|
@@ -484,7 +521,7 @@ const calculateDiffDecorationsInner = ({
|
|
|
484
521
|
isInserted: true
|
|
485
522
|
}));
|
|
486
523
|
});
|
|
487
|
-
getAttrChangeRanges(tr.doc,
|
|
524
|
+
getAttrChangeRanges(tr.doc, attrStepContexts, originalDoc).forEach(change => {
|
|
488
525
|
if (change.isInline) {
|
|
489
526
|
// Inline nodes (e.g. date, emoji, mention, status) need an inline decoration rather than a block decoration
|
|
490
527
|
const isActive = activeIndexPos && change.fromB === activeIndexPos.from && change.toB === activeIndexPos.to;
|
|
@@ -1,7 +1,10 @@
|
|
|
1
|
+
import isEqual from 'lodash/isEqual';
|
|
2
|
+
import omit from 'lodash/omit';
|
|
1
3
|
import { SetAttrsStep } from '@atlaskit/adf-schema/steps';
|
|
2
4
|
import { isExperimentEnabled } from '@atlaskit/editor-common/deprecated-platform-feature-experiments';
|
|
3
5
|
import { getBaseNodeTypeName } from '@atlaskit/editor-common/utils/node-type-utils';
|
|
4
6
|
import { AttrStep } from '@atlaskit/editor-prosemirror/transform';
|
|
7
|
+
import { fg } from '@atlaskit/platform-feature-flags/fg';
|
|
5
8
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
6
9
|
import { getRequiredIncludedDiffableAttrs, isDiffableAttr } from './diffableAttrs';
|
|
7
10
|
const filterUndefined = x => !!x;
|
|
@@ -27,29 +30,49 @@ const isInlineAttrChangeNodeName = nodeName => nodeName in inlineNodeAttrMap;
|
|
|
27
30
|
// Extension node type names. Their "any attr except localId" exclude rule lives
|
|
28
31
|
// in the shared `diffableAttrs` map and is applied via `isDiffableAttr` below.
|
|
29
32
|
const extensionNodeNames = ['extension', 'inlineExtension', 'bodiedExtension'];
|
|
33
|
+
const transientExtensionAttrPaths = ['localId', 'parameters.macroParams._parentId'];
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Removes extension metadata that can change between document versions without changing the
|
|
37
|
+
* extension's user-visible configuration.
|
|
38
|
+
*/
|
|
39
|
+
const getComparableExtensionAttrs = node => omit(node.attrs, transientExtensionAttrPaths);
|
|
40
|
+
const haveSameRelevantExtensionAttrs = (beforeNode, afterNode) => isEqual(getComparableExtensionAttrs(beforeNode), getComparableExtensionAttrs(afterNode));
|
|
30
41
|
const getStepAttrs = step => {
|
|
31
42
|
if (step instanceof AttrStep) {
|
|
32
43
|
return [step.attr];
|
|
33
44
|
}
|
|
34
|
-
if (step
|
|
45
|
+
if (step.attrs) {
|
|
35
46
|
return Object.keys(step.attrs);
|
|
36
47
|
}
|
|
37
48
|
return [];
|
|
38
49
|
};
|
|
39
|
-
export const getAttrChangeRanges = (doc,
|
|
40
|
-
return
|
|
50
|
+
export const getAttrChangeRanges = (doc, attrStepContexts, originalDoc) => {
|
|
51
|
+
return attrStepContexts.map(attrStepContext => {
|
|
52
|
+
const {
|
|
53
|
+
afterNode,
|
|
54
|
+
beforeNode,
|
|
55
|
+
finalPos,
|
|
56
|
+
originalPos,
|
|
57
|
+
step
|
|
58
|
+
} = attrStepContext;
|
|
41
59
|
if (!(step instanceof AttrStep) && !(step instanceof SetAttrsStep)) {
|
|
42
60
|
return undefined;
|
|
43
61
|
}
|
|
44
62
|
const stepAttrs = getStepAttrs(step);
|
|
45
|
-
|
|
46
|
-
|
|
63
|
+
// SetAttrsStep contains the complete replacement attrs, not only the attrs that changed.
|
|
64
|
+
// Keep the legacy payload-based checks until the rollout gate is enabled, and fall back
|
|
65
|
+
// to them if either step-time node is unavailable.
|
|
66
|
+
const attrsToCheck = fg('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode ? stepAttrs.filter(attrName => !isEqual(beforeNode.attrs[attrName], afterNode.attrs[attrName])) : stepAttrs;
|
|
67
|
+
const $pos = doc.resolve(finalPos);
|
|
68
|
+
const nodeAtPos = doc.nodeAt(finalPos);
|
|
69
|
+
const originalNodeAtPos = originalPos === undefined ? null : originalDoc.nodeAt(originalPos);
|
|
47
70
|
|
|
48
71
|
// date node: timestamp attribute change — highlight the date node itself (inline)
|
|
49
|
-
if (
|
|
72
|
+
if (attrsToCheck.some(v => dateAttrs.includes(v)) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'date' && !isExperimentEnabled('platform_editor_improve_inline_diffs', () => expValEquals('platform_editor_improve_inline_diffs', 'isEnabled', true))) {
|
|
50
73
|
return {
|
|
51
|
-
fromB:
|
|
52
|
-
toB:
|
|
74
|
+
fromB: finalPos,
|
|
75
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
53
76
|
isInline: true,
|
|
54
77
|
inlineNodeName: 'date'
|
|
55
78
|
};
|
|
@@ -62,16 +85,15 @@ export const getAttrChangeRanges = (doc, steps, originalDoc) => {
|
|
|
62
85
|
const nodeName = nodeAtPos.type.name;
|
|
63
86
|
if (isInlineAttrChangeNodeName(nodeName)) {
|
|
64
87
|
const watchedAttrs = inlineNodeAttrMap[nodeName];
|
|
65
|
-
if (
|
|
66
|
-
const originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
88
|
+
if (attrsToCheck.some(v => watchedAttrs.includes(v))) {
|
|
67
89
|
return {
|
|
68
|
-
fromB:
|
|
69
|
-
toB:
|
|
90
|
+
fromB: finalPos,
|
|
91
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
70
92
|
isInline: true,
|
|
71
93
|
inlineNodeName: nodeName,
|
|
72
|
-
...(originalNodeAtPos && {
|
|
73
|
-
fromA:
|
|
74
|
-
toA:
|
|
94
|
+
...(originalPos !== undefined && originalNodeAtPos && {
|
|
95
|
+
fromA: originalPos,
|
|
96
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
75
97
|
})
|
|
76
98
|
};
|
|
77
99
|
}
|
|
@@ -79,10 +101,10 @@ export const getAttrChangeRanges = (doc, steps, originalDoc) => {
|
|
|
79
101
|
}
|
|
80
102
|
|
|
81
103
|
// taskItem node: state attribute change — highlight the taskItem node
|
|
82
|
-
if (
|
|
104
|
+
if (attrsToCheck.some(v => taskItemAttrs.includes(v)) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'taskItem') {
|
|
83
105
|
return {
|
|
84
|
-
fromB:
|
|
85
|
-
toB:
|
|
106
|
+
fromB: finalPos,
|
|
107
|
+
toB: finalPos + nodeAtPos.nodeSize
|
|
86
108
|
};
|
|
87
109
|
}
|
|
88
110
|
|
|
@@ -90,30 +112,33 @@ export const getAttrChangeRanges = (doc, steps, originalDoc) => {
|
|
|
90
112
|
// (e.g. note -> warning) — highlight the new panel and, when the original node
|
|
91
113
|
// is resolvable, expose its range (fromA/toA) so the caller can render the old
|
|
92
114
|
// panel as a "deleted" widget for a before/after comparison.
|
|
93
|
-
if (
|
|
94
|
-
const originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
115
|
+
if (attrsToCheck.some(v => panelAttrs.includes(v)) && nodeAtPos && getBaseNodeTypeName(nodeAtPos.type) === 'panel') {
|
|
95
116
|
return {
|
|
96
|
-
fromB:
|
|
97
|
-
toB:
|
|
98
|
-
...(originalNodeAtPos && {
|
|
99
|
-
fromA:
|
|
100
|
-
toA:
|
|
117
|
+
fromB: finalPos,
|
|
118
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
119
|
+
...(originalPos !== undefined && originalNodeAtPos && {
|
|
120
|
+
fromA: originalPos,
|
|
121
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
101
122
|
})
|
|
102
123
|
};
|
|
103
124
|
}
|
|
104
125
|
|
|
105
|
-
//
|
|
106
|
-
|
|
126
|
+
// Extension nodes: highlight changes to user-visible configuration. When enabled,
|
|
127
|
+
// transient extension metadata is ignored by the comparison below.
|
|
128
|
+
if (nodeAtPos && extensionNodeNames.includes(nodeAtPos.type.name) && attrsToCheck.some(v => isDiffableAttr(nodeAtPos.type.name, v))) {
|
|
129
|
+
if (fg('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode && beforeNode.type === afterNode.type && haveSameRelevantExtensionAttrs(beforeNode, afterNode)) {
|
|
130
|
+
return undefined;
|
|
131
|
+
}
|
|
107
132
|
const isInline = nodeAtPos.type.name === 'inlineExtension';
|
|
108
133
|
return {
|
|
109
|
-
fromB:
|
|
110
|
-
toB:
|
|
134
|
+
fromB: finalPos,
|
|
135
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
111
136
|
isInline
|
|
112
137
|
};
|
|
113
138
|
}
|
|
114
139
|
|
|
115
140
|
// media node: id/collection/url attribute change — highlight the mediaSingle parent
|
|
116
|
-
if (
|
|
141
|
+
if (attrsToCheck.some(v => mediaAttrs.includes(v)) && $pos.parent.type === doc.type.schema.nodes.mediaSingle) {
|
|
117
142
|
const startPos = $pos.pos + $pos.parentOffset;
|
|
118
143
|
return {
|
|
119
144
|
fromB: startPos,
|
|
@@ -11,6 +11,7 @@ import memoizeOne from 'memoize-one';
|
|
|
11
11
|
import { ChangeSet, simplifyChanges } from 'prosemirror-changeset';
|
|
12
12
|
import { isExperimentEnabled } from '@atlaskit/editor-common/deprecated-platform-feature-experiments';
|
|
13
13
|
import { areNodesEqualIgnoreAttrs } from '@atlaskit/editor-common/utils/document';
|
|
14
|
+
import { Mapping } from '@atlaskit/editor-prosemirror/transform';
|
|
14
15
|
import { DecorationSet } from '@atlaskit/editor-prosemirror/view';
|
|
15
16
|
import { fg } from '@atlaskit/platform-feature-flags/fg';
|
|
16
17
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
@@ -287,7 +288,7 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
287
288
|
} else {
|
|
288
289
|
simplifiedSteps = simplifySteps(steps, originalDoc);
|
|
289
290
|
}
|
|
290
|
-
var
|
|
291
|
+
var pendingAttrSteps = [];
|
|
291
292
|
var stepMaps = [];
|
|
292
293
|
var _iterator = _createForOfIteratorHelper(simplifiedSteps),
|
|
293
294
|
_step;
|
|
@@ -297,20 +298,56 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
297
298
|
var result = step.apply(steppedDoc);
|
|
298
299
|
if (result.failed === null && result.doc) {
|
|
299
300
|
if (stepIsValidAttrChange(step, steppedDoc, result.doc)) {
|
|
300
|
-
|
|
301
|
+
pendingAttrSteps.push({
|
|
302
|
+
afterNode: result.doc.nodeAt(step.pos),
|
|
303
|
+
beforeNode: steppedDoc.nodeAt(step.pos),
|
|
304
|
+
mapIndex: stepMaps.length,
|
|
305
|
+
step: step
|
|
306
|
+
});
|
|
301
307
|
}
|
|
302
308
|
stepMaps.push(step.getMap());
|
|
303
309
|
steppedDoc = result.doc;
|
|
304
310
|
}
|
|
305
311
|
}
|
|
306
|
-
|
|
307
|
-
//
|
|
308
|
-
// changes and ignores differences in attributes which don't affect decoration positions
|
|
312
|
+
// Gate the complete attribution fix: mapped positions and step-time nodes are used together.
|
|
313
|
+
// The fallback deliberately preserves the legacy raw-position lookups for rollout safety.
|
|
309
314
|
} catch (err) {
|
|
310
315
|
_iterator.e(err);
|
|
311
316
|
} finally {
|
|
312
317
|
_iterator.f();
|
|
313
318
|
}
|
|
319
|
+
var attrStepContexts = fg('platform_editor_reduce_diff_attr_sensitivity') ? pendingAttrSteps.flatMap(function (_ref0) {
|
|
320
|
+
var afterNode = _ref0.afterNode,
|
|
321
|
+
beforeNode = _ref0.beforeNode,
|
|
322
|
+
mapIndex = _ref0.mapIndex,
|
|
323
|
+
step = _ref0.step;
|
|
324
|
+
var finalPosition = new Mapping(stepMaps.slice(mapIndex + 1)).mapResult(step.pos);
|
|
325
|
+
if (finalPosition.deleted) {
|
|
326
|
+
return [];
|
|
327
|
+
}
|
|
328
|
+
var originalPosition = new Mapping(stepMaps.slice(0, mapIndex)).invert().mapResult(step.pos);
|
|
329
|
+
return [_objectSpread(_objectSpread({
|
|
330
|
+
afterNode: afterNode,
|
|
331
|
+
beforeNode: beforeNode,
|
|
332
|
+
finalPos: finalPosition.pos
|
|
333
|
+
}, originalPosition.deleted ? {} : {
|
|
334
|
+
originalPos: originalPosition.pos
|
|
335
|
+
}), {}, {
|
|
336
|
+
step: step
|
|
337
|
+
})];
|
|
338
|
+
}) : pendingAttrSteps.map(function (_ref1) {
|
|
339
|
+
var step = _ref1.step;
|
|
340
|
+
return {
|
|
341
|
+
afterNode: tr.doc.nodeAt(step.pos),
|
|
342
|
+
beforeNode: originalDoc.nodeAt(step.pos),
|
|
343
|
+
finalPos: step.pos,
|
|
344
|
+
originalPos: step.pos,
|
|
345
|
+
step: step
|
|
346
|
+
};
|
|
347
|
+
});
|
|
348
|
+
|
|
349
|
+
// Rather than using .eq() we use a custom function that only checks for structural
|
|
350
|
+
// changes and ignores differences in attributes which don't affect decoration positions
|
|
314
351
|
if (!areNodesEqualIgnoreAttrs(steppedDoc, tr.doc)) {
|
|
315
352
|
var _api$analytics;
|
|
316
353
|
var recoveredViaContentEquality = areDocsEqualByBlockStructureAndText(steppedDoc, tr.doc);
|
|
@@ -524,7 +561,7 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
524
561
|
isInserted: true
|
|
525
562
|
})));
|
|
526
563
|
});
|
|
527
|
-
getAttrChangeRanges(tr.doc,
|
|
564
|
+
getAttrChangeRanges(tr.doc, attrStepContexts, originalDoc).forEach(function (change) {
|
|
528
565
|
if (change.isInline) {
|
|
529
566
|
// Inline nodes (e.g. date, emoji, mention, status) need an inline decoration rather than a block decoration
|
|
530
567
|
var isActive = activeIndexPos && change.fromB === activeIndexPos.from && change.toB === activeIndexPos.to;
|
|
@@ -614,42 +651,42 @@ var calculateDiffDecorationsInner = function calculateDiffDecorationsInner(_ref7
|
|
|
614
651
|
};
|
|
615
652
|
export var calculateDiffDecorations = memoizeOne(calculateDiffDecorationsInner,
|
|
616
653
|
// Cache results unless relevant inputs change
|
|
617
|
-
function (
|
|
618
|
-
var
|
|
619
|
-
var
|
|
620
|
-
|
|
621
|
-
pluginState =
|
|
622
|
-
state =
|
|
623
|
-
colorScheme =
|
|
624
|
-
intl =
|
|
625
|
-
activeIndexPos =
|
|
626
|
-
isInverted =
|
|
627
|
-
diffType =
|
|
628
|
-
hideDeletedDiffs =
|
|
629
|
-
hideAddedDiffsUnderline =
|
|
630
|
-
showIndicators =
|
|
631
|
-
smartThresholds =
|
|
632
|
-
deletedDiffPlacement =
|
|
633
|
-
inlineDeletedDiffPlacement =
|
|
634
|
-
var
|
|
635
|
-
|
|
636
|
-
lastPluginState =
|
|
637
|
-
lastState =
|
|
638
|
-
lastColorScheme =
|
|
639
|
-
lastIntl =
|
|
640
|
-
lastActiveIndexPos =
|
|
641
|
-
lastIsInverted =
|
|
642
|
-
lastDiffType =
|
|
643
|
-
lastHideDeletedDiffs =
|
|
644
|
-
lastHideAddedDiffsUnderline =
|
|
645
|
-
lastShowIndicators =
|
|
646
|
-
lastSmartThresholds =
|
|
647
|
-
lastDeletedDiffPlacement =
|
|
648
|
-
lastInlineDeletedDiffPlacement =
|
|
654
|
+
function (_ref10, _ref11) {
|
|
655
|
+
var _ref15;
|
|
656
|
+
var _ref12 = _slicedToArray(_ref10, 1),
|
|
657
|
+
_ref12$ = _ref12[0],
|
|
658
|
+
pluginState = _ref12$.pluginState,
|
|
659
|
+
state = _ref12$.state,
|
|
660
|
+
colorScheme = _ref12$.colorScheme,
|
|
661
|
+
intl = _ref12$.intl,
|
|
662
|
+
activeIndexPos = _ref12$.activeIndexPos,
|
|
663
|
+
isInverted = _ref12$.isInverted,
|
|
664
|
+
diffType = _ref12$.diffType,
|
|
665
|
+
hideDeletedDiffs = _ref12$.hideDeletedDiffs,
|
|
666
|
+
hideAddedDiffsUnderline = _ref12$.hideAddedDiffsUnderline,
|
|
667
|
+
showIndicators = _ref12$.showIndicators,
|
|
668
|
+
smartThresholds = _ref12$.smartThresholds,
|
|
669
|
+
deletedDiffPlacement = _ref12$.deletedDiffPlacement,
|
|
670
|
+
inlineDeletedDiffPlacement = _ref12$.inlineDeletedDiffPlacement;
|
|
671
|
+
var _ref13 = _slicedToArray(_ref11, 1),
|
|
672
|
+
_ref13$ = _ref13[0],
|
|
673
|
+
lastPluginState = _ref13$.pluginState,
|
|
674
|
+
lastState = _ref13$.state,
|
|
675
|
+
lastColorScheme = _ref13$.colorScheme,
|
|
676
|
+
lastIntl = _ref13$.intl,
|
|
677
|
+
lastActiveIndexPos = _ref13$.activeIndexPos,
|
|
678
|
+
lastIsInverted = _ref13$.isInverted,
|
|
679
|
+
lastDiffType = _ref13$.diffType,
|
|
680
|
+
lastHideDeletedDiffs = _ref13$.hideDeletedDiffs,
|
|
681
|
+
lastHideAddedDiffsUnderline = _ref13$.hideAddedDiffsUnderline,
|
|
682
|
+
lastShowIndicators = _ref13$.showIndicators,
|
|
683
|
+
lastSmartThresholds = _ref13$.smartThresholds,
|
|
684
|
+
lastDeletedDiffPlacement = _ref13$.deletedDiffPlacement,
|
|
685
|
+
lastInlineDeletedDiffPlacement = _ref13$.inlineDeletedDiffPlacement;
|
|
649
686
|
var originalDocIsSame = lastPluginState.originalDoc && pluginState.originalDoc && pluginState.originalDoc.eq(lastPluginState.originalDoc);
|
|
650
687
|
if (isExtendedEnabled(diffType)) {
|
|
651
|
-
var
|
|
652
|
-
return (
|
|
688
|
+
var _ref14;
|
|
689
|
+
return (_ref14 = colorScheme === lastColorScheme && intl.locale === lastIntl.locale && isInverted === lastIsInverted && diffType === lastDiffType && isEqual(activeIndexPos, lastActiveIndexPos) && originalDocIsSame && isEqual(pluginState.steps, lastPluginState.steps) && isEqual(pluginState.stepAttributions, lastPluginState.stepAttributions) && state.doc.eq(lastState.doc) && hideDeletedDiffs === lastHideDeletedDiffs && hideAddedDiffsUnderline === lastHideAddedDiffsUnderline && showIndicators === lastShowIndicators && isEqual(smartThresholds, lastSmartThresholds) && deletedDiffPlacement === lastDeletedDiffPlacement && inlineDeletedDiffPlacement === lastInlineDeletedDiffPlacement) !== null && _ref14 !== void 0 ? _ref14 : false;
|
|
653
690
|
}
|
|
654
|
-
return (
|
|
691
|
+
return (_ref15 = originalDocIsSame && isEqual(pluginState.steps, lastPluginState.steps) && isEqual(pluginState.stepAttributions, lastPluginState.stepAttributions) && state.doc.eq(lastState.doc) && colorScheme === lastColorScheme && intl.locale === lastIntl.locale && isEqual(activeIndexPos, lastActiveIndexPos) && hideDeletedDiffs === lastHideDeletedDiffs) !== null && _ref15 !== void 0 ? _ref15 : false;
|
|
655
692
|
});
|
|
@@ -1,10 +1,13 @@
|
|
|
1
1
|
import _defineProperty from "@babel/runtime/helpers/defineProperty";
|
|
2
2
|
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
3
3
|
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
|
|
4
|
+
import isEqual from 'lodash/isEqual';
|
|
5
|
+
import omit from 'lodash/omit';
|
|
4
6
|
import { SetAttrsStep } from '@atlaskit/adf-schema/steps';
|
|
5
7
|
import { isExperimentEnabled } from '@atlaskit/editor-common/deprecated-platform-feature-experiments';
|
|
6
8
|
import { getBaseNodeTypeName } from '@atlaskit/editor-common/utils/node-type-utils';
|
|
7
9
|
import { AttrStep } from '@atlaskit/editor-prosemirror/transform';
|
|
10
|
+
import { fg } from '@atlaskit/platform-feature-flags/fg';
|
|
8
11
|
import { expValEquals } from '@atlaskit/tmp-editor-statsig/exp-val-equals';
|
|
9
12
|
import { getRequiredIncludedDiffableAttrs, isDiffableAttr } from './diffableAttrs';
|
|
10
13
|
var filterUndefined = function filterUndefined(x) {
|
|
@@ -34,33 +37,57 @@ var isInlineAttrChangeNodeName = function isInlineAttrChangeNodeName(nodeName) {
|
|
|
34
37
|
// Extension node type names. Their "any attr except localId" exclude rule lives
|
|
35
38
|
// in the shared `diffableAttrs` map and is applied via `isDiffableAttr` below.
|
|
36
39
|
var extensionNodeNames = ['extension', 'inlineExtension', 'bodiedExtension'];
|
|
40
|
+
var transientExtensionAttrPaths = ['localId', 'parameters.macroParams._parentId'];
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Removes extension metadata that can change between document versions without changing the
|
|
44
|
+
* extension's user-visible configuration.
|
|
45
|
+
*/
|
|
46
|
+
var getComparableExtensionAttrs = function getComparableExtensionAttrs(node) {
|
|
47
|
+
return omit(node.attrs, transientExtensionAttrPaths);
|
|
48
|
+
};
|
|
49
|
+
var haveSameRelevantExtensionAttrs = function haveSameRelevantExtensionAttrs(beforeNode, afterNode) {
|
|
50
|
+
return isEqual(getComparableExtensionAttrs(beforeNode), getComparableExtensionAttrs(afterNode));
|
|
51
|
+
};
|
|
37
52
|
var getStepAttrs = function getStepAttrs(step) {
|
|
38
53
|
if (step instanceof AttrStep) {
|
|
39
54
|
return [step.attr];
|
|
40
55
|
}
|
|
41
|
-
if (step
|
|
56
|
+
if (step.attrs) {
|
|
42
57
|
return Object.keys(step.attrs);
|
|
43
58
|
}
|
|
44
59
|
return [];
|
|
45
60
|
};
|
|
46
|
-
export var getAttrChangeRanges = function getAttrChangeRanges(doc,
|
|
47
|
-
return
|
|
61
|
+
export var getAttrChangeRanges = function getAttrChangeRanges(doc, attrStepContexts, originalDoc) {
|
|
62
|
+
return attrStepContexts.map(function (attrStepContext) {
|
|
63
|
+
var afterNode = attrStepContext.afterNode,
|
|
64
|
+
beforeNode = attrStepContext.beforeNode,
|
|
65
|
+
finalPos = attrStepContext.finalPos,
|
|
66
|
+
originalPos = attrStepContext.originalPos,
|
|
67
|
+
step = attrStepContext.step;
|
|
48
68
|
if (!(step instanceof AttrStep) && !(step instanceof SetAttrsStep)) {
|
|
49
69
|
return undefined;
|
|
50
70
|
}
|
|
51
71
|
var stepAttrs = getStepAttrs(step);
|
|
52
|
-
|
|
53
|
-
|
|
72
|
+
// SetAttrsStep contains the complete replacement attrs, not only the attrs that changed.
|
|
73
|
+
// Keep the legacy payload-based checks until the rollout gate is enabled, and fall back
|
|
74
|
+
// to them if either step-time node is unavailable.
|
|
75
|
+
var attrsToCheck = fg('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode ? stepAttrs.filter(function (attrName) {
|
|
76
|
+
return !isEqual(beforeNode.attrs[attrName], afterNode.attrs[attrName]);
|
|
77
|
+
}) : stepAttrs;
|
|
78
|
+
var $pos = doc.resolve(finalPos);
|
|
79
|
+
var nodeAtPos = doc.nodeAt(finalPos);
|
|
80
|
+
var originalNodeAtPos = originalPos === undefined ? null : originalDoc.nodeAt(originalPos);
|
|
54
81
|
|
|
55
82
|
// date node: timestamp attribute change — highlight the date node itself (inline)
|
|
56
|
-
if (
|
|
83
|
+
if (attrsToCheck.some(function (v) {
|
|
57
84
|
return dateAttrs.includes(v);
|
|
58
85
|
}) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'date' && !isExperimentEnabled('platform_editor_improve_inline_diffs', function () {
|
|
59
86
|
return expValEquals('platform_editor_improve_inline_diffs', 'isEnabled', true);
|
|
60
87
|
})) {
|
|
61
88
|
return {
|
|
62
|
-
fromB:
|
|
63
|
-
toB:
|
|
89
|
+
fromB: finalPos,
|
|
90
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
64
91
|
isInline: true,
|
|
65
92
|
inlineNodeName: 'date'
|
|
66
93
|
};
|
|
@@ -75,30 +102,29 @@ export var getAttrChangeRanges = function getAttrChangeRanges(doc, steps, origin
|
|
|
75
102
|
var nodeName = nodeAtPos.type.name;
|
|
76
103
|
if (isInlineAttrChangeNodeName(nodeName)) {
|
|
77
104
|
var watchedAttrs = inlineNodeAttrMap[nodeName];
|
|
78
|
-
if (
|
|
105
|
+
if (attrsToCheck.some(function (v) {
|
|
79
106
|
return watchedAttrs.includes(v);
|
|
80
107
|
})) {
|
|
81
|
-
var originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
82
108
|
return _objectSpread({
|
|
83
|
-
fromB:
|
|
84
|
-
toB:
|
|
109
|
+
fromB: finalPos,
|
|
110
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
85
111
|
isInline: true,
|
|
86
112
|
inlineNodeName: nodeName
|
|
87
|
-
}, originalNodeAtPos && {
|
|
88
|
-
fromA:
|
|
89
|
-
toA:
|
|
113
|
+
}, originalPos !== undefined && originalNodeAtPos && {
|
|
114
|
+
fromA: originalPos,
|
|
115
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
90
116
|
});
|
|
91
117
|
}
|
|
92
118
|
}
|
|
93
119
|
}
|
|
94
120
|
|
|
95
121
|
// taskItem node: state attribute change — highlight the taskItem node
|
|
96
|
-
if (
|
|
122
|
+
if (attrsToCheck.some(function (v) {
|
|
97
123
|
return taskItemAttrs.includes(v);
|
|
98
124
|
}) && (nodeAtPos === null || nodeAtPos === void 0 ? void 0 : nodeAtPos.type.name) === 'taskItem') {
|
|
99
125
|
return {
|
|
100
|
-
fromB:
|
|
101
|
-
toB:
|
|
126
|
+
fromB: finalPos,
|
|
127
|
+
toB: finalPos + nodeAtPos.nodeSize
|
|
102
128
|
};
|
|
103
129
|
}
|
|
104
130
|
|
|
@@ -106,33 +132,36 @@ export var getAttrChangeRanges = function getAttrChangeRanges(doc, steps, origin
|
|
|
106
132
|
// (e.g. note -> warning) — highlight the new panel and, when the original node
|
|
107
133
|
// is resolvable, expose its range (fromA/toA) so the caller can render the old
|
|
108
134
|
// panel as a "deleted" widget for a before/after comparison.
|
|
109
|
-
if (
|
|
135
|
+
if (attrsToCheck.some(function (v) {
|
|
110
136
|
return panelAttrs.includes(v);
|
|
111
137
|
}) && nodeAtPos && getBaseNodeTypeName(nodeAtPos.type) === 'panel') {
|
|
112
|
-
var _originalNodeAtPos = originalDoc === null || originalDoc === void 0 ? void 0 : originalDoc.nodeAt(step.pos);
|
|
113
138
|
return _objectSpread({
|
|
114
|
-
fromB:
|
|
115
|
-
toB:
|
|
116
|
-
},
|
|
117
|
-
fromA:
|
|
118
|
-
toA:
|
|
139
|
+
fromB: finalPos,
|
|
140
|
+
toB: finalPos + nodeAtPos.nodeSize
|
|
141
|
+
}, originalPos !== undefined && originalNodeAtPos && {
|
|
142
|
+
fromA: originalPos,
|
|
143
|
+
toA: originalPos + originalNodeAtPos.nodeSize
|
|
119
144
|
});
|
|
120
145
|
}
|
|
121
146
|
|
|
122
|
-
//
|
|
123
|
-
|
|
147
|
+
// Extension nodes: highlight changes to user-visible configuration. When enabled,
|
|
148
|
+
// transient extension metadata is ignored by the comparison below.
|
|
149
|
+
if (nodeAtPos && extensionNodeNames.includes(nodeAtPos.type.name) && attrsToCheck.some(function (v) {
|
|
124
150
|
return isDiffableAttr(nodeAtPos.type.name, v);
|
|
125
151
|
})) {
|
|
152
|
+
if (fg('platform_editor_reduce_diff_attr_sensitivity') && beforeNode && afterNode && beforeNode.type === afterNode.type && haveSameRelevantExtensionAttrs(beforeNode, afterNode)) {
|
|
153
|
+
return undefined;
|
|
154
|
+
}
|
|
126
155
|
var isInline = nodeAtPos.type.name === 'inlineExtension';
|
|
127
156
|
return {
|
|
128
|
-
fromB:
|
|
129
|
-
toB:
|
|
157
|
+
fromB: finalPos,
|
|
158
|
+
toB: finalPos + nodeAtPos.nodeSize,
|
|
130
159
|
isInline: isInline
|
|
131
160
|
};
|
|
132
161
|
}
|
|
133
162
|
|
|
134
163
|
// media node: id/collection/url attribute change — highlight the mediaSingle parent
|
|
135
|
-
if (
|
|
164
|
+
if (attrsToCheck.some(function (v) {
|
|
136
165
|
return mediaAttrs.includes(v);
|
|
137
166
|
}) && $pos.parent.type === doc.type.schema.nodes.mediaSingle) {
|
|
138
167
|
var startPos = $pos.pos + $pos.parentOffset;
|
|
@@ -1,6 +1,16 @@
|
|
|
1
|
+
import { SetAttrsStep } from '@atlaskit/adf-schema/steps';
|
|
1
2
|
import type { Node as PMNode } from '@atlaskit/editor-prosemirror/model';
|
|
2
3
|
import type { Step as ProseMirrorStep } from '@atlaskit/editor-prosemirror/transform-override';
|
|
4
|
+
import { AttrStep } from '@atlaskit/editor-prosemirror/transform';
|
|
3
5
|
export type InlineAttrChangeNodeName = 'date' | 'emoji' | 'mention' | 'status';
|
|
6
|
+
type AttrChangeStep = AttrStep | SetAttrsStep;
|
|
7
|
+
export type AttrStepContext = {
|
|
8
|
+
afterNode: PMNode | null;
|
|
9
|
+
beforeNode: PMNode | null;
|
|
10
|
+
finalPos: number;
|
|
11
|
+
originalPos?: number;
|
|
12
|
+
step: AttrChangeStep;
|
|
13
|
+
};
|
|
4
14
|
type StepRange = {
|
|
5
15
|
/**
|
|
6
16
|
* Position of the original (before) node in the original doc.
|
|
@@ -16,7 +26,7 @@ type StepRange = {
|
|
|
16
26
|
toA?: number;
|
|
17
27
|
toB: number;
|
|
18
28
|
};
|
|
19
|
-
export declare const getAttrChangeRanges: (doc: PMNode,
|
|
29
|
+
export declare const getAttrChangeRanges: (doc: PMNode, attrStepContexts: AttrStepContext[], originalDoc: PMNode) => StepRange[];
|
|
20
30
|
/**
|
|
21
31
|
* Check if the step was a valid attr change and affected the doc
|
|
22
32
|
*
|
|
@@ -25,5 +35,5 @@ export declare const getAttrChangeRanges: (doc: PMNode, steps: ProseMirrorStep[]
|
|
|
25
35
|
* @param afterDoc Doc after the step
|
|
26
36
|
* @returns Boolean if the change should show a decoration
|
|
27
37
|
*/
|
|
28
|
-
export declare const stepIsValidAttrChange: (step: ProseMirrorStep, beforeDoc: PMNode, afterDoc: PMNode) =>
|
|
38
|
+
export declare const stepIsValidAttrChange: (step: ProseMirrorStep, beforeDoc: PMNode, afterDoc: PMNode) => step is AttrChangeStep;
|
|
29
39
|
export {};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@atlaskit/editor-plugin-show-diff",
|
|
3
|
-
"version": "14.1.
|
|
3
|
+
"version": "14.1.1",
|
|
4
4
|
"description": "ShowDiff plugin for @atlaskit/editor-core",
|
|
5
5
|
"author": "Atlassian Pty Ltd",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
"sideEffects": false,
|
|
21
21
|
"atlaskit:src": "src/index.ts",
|
|
22
22
|
"dependencies": {
|
|
23
|
-
"@atlaskit/adf-schema": "^57.
|
|
23
|
+
"@atlaskit/adf-schema": "^57.2.0",
|
|
24
24
|
"@atlaskit/custom-steps": "^1.0.0",
|
|
25
25
|
"@atlaskit/editor-plugin-analytics": "^16.0.0",
|
|
26
26
|
"@atlaskit/editor-plugin-user-intent": "^14.0.0",
|
|
@@ -28,7 +28,7 @@
|
|
|
28
28
|
"@atlaskit/editor-tables": "^3.0.0",
|
|
29
29
|
"@atlaskit/platform-feature-experiments": "^0.3.0",
|
|
30
30
|
"@atlaskit/platform-feature-flags": "^2.1.0",
|
|
31
|
-
"@atlaskit/tmp-editor-statsig": "^
|
|
31
|
+
"@atlaskit/tmp-editor-statsig": "^163.0.0",
|
|
32
32
|
"@atlaskit/tokens": "^16.8.0",
|
|
33
33
|
"@babel/runtime": "^7.0.0",
|
|
34
34
|
"@compiled/react": "^1.0.2",
|
|
@@ -39,9 +39,9 @@
|
|
|
39
39
|
"devDependencies": {
|
|
40
40
|
"@atlaskit/adf-utils": "^20.7.0",
|
|
41
41
|
"@atlaskit/button": "^25.2.0",
|
|
42
|
-
"@atlaskit/css": "^1.
|
|
42
|
+
"@atlaskit/css": "^1.1.0",
|
|
43
43
|
"@atlaskit/dropdown-menu": "^18.2.0",
|
|
44
|
-
"@atlaskit/editor-core": "^226.
|
|
44
|
+
"@atlaskit/editor-core": "^226.1.0",
|
|
45
45
|
"@atlaskit/editor-json-transformer": "^9.6.0",
|
|
46
46
|
"@atlaskit/editor-plugins": "^16.1.0",
|
|
47
47
|
"@atlaskit/form": "^17.1.0",
|
|
@@ -104,6 +104,9 @@
|
|
|
104
104
|
},
|
|
105
105
|
"confluence_ncs_step_diffing_version_history": {
|
|
106
106
|
"type": "boolean"
|
|
107
|
+
},
|
|
108
|
+
"platform_editor_reduce_diff_attr_sensitivity": {
|
|
109
|
+
"type": "boolean"
|
|
107
110
|
}
|
|
108
111
|
}
|
|
109
112
|
}
|