Skip to content

Commit 03b0f69

Browse files
committed
Fix order patches
1 parent f3373de commit 03b0f69

File tree

3 files changed

+99
-85
lines changed

3 files changed

+99
-85
lines changed

index.js

Lines changed: 34 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -167,27 +167,24 @@ function reorder(leftChildren, rightChildren) {
167167
var rightChildIndex = keyIndex(rightChildren);
168168
var rightKeys = rightChildIndex.key;
169169
var rightIndex = rightChildIndex.index;
170-
var removes = [];
171-
var inserts = [];
172170
var leftLength = leftChildren.length;
173171
var rightLength = rightChildren.length;
174172
var leftOffset = 0;
175173
var rightOffset = 0;
176-
var leftKey = leftIndex[leftOffset];
177-
var rightKey = rightIndex[rightOffset];
178-
var leftMoved = [];
179174
var rightMoved = [];
180-
var leftDistance;
181-
var rightDistance;
182-
var index = -1;
175+
var leftMoved = [];
176+
var removes = [];
177+
var inserts = [];
183178
var next = [];
184-
var key;
179+
var index = -1;
180+
var leftKey;
181+
var rightKey;
185182

186183
while (++index < leftLength) {
187-
key = leftIndex[index];
184+
leftKey = leftIndex[index];
188185

189-
if (key in rightKeys) {
190-
next.push(rightChildren[rightKeys[key]]);
186+
if (leftKey in rightKeys) {
187+
next.push(rightChildren[rightKeys[leftKey]]);
191188
} else {
192189
next.push(null);
193190
}
@@ -196,75 +193,52 @@ function reorder(leftChildren, rightChildren) {
196193
index = -1;
197194

198195
while (++index < rightLength) {
199-
key = rightIndex[index];
200-
201-
if (!(key in leftKeys)) {
196+
if (!(rightIndex[index] in leftKeys)) {
202197
next.push(rightChildren[index]);
203198
}
204199
}
205200

201+
leftChildren = next;
202+
leftChildIndex = keyIndex(leftChildren);
203+
leftKeys = leftChildIndex.key;
204+
leftIndex = leftChildIndex.index;
205+
leftLength = leftChildren.length;
206+
rightKey = rightIndex[rightOffset];
207+
leftKey = leftIndex[leftOffset];
208+
206209
while (leftOffset < leftLength || rightOffset < rightLength) {
207210
/* The left node moved already. */
208211
if (leftMoved.indexOf(leftOffset) !== -1) {
209-
removes.push({
210-
from: leftOffset,
211-
left: leftChildren[leftOffset],
212-
right: rightChildren[rightKeys[leftKey]]
213-
});
214-
212+
removes.push({left: leftChildren[leftOffset], right: leftOffset});
215213
leftKey = leftIndex[++leftOffset];
216214
/* The right node moved already. */
217215
} else if (rightMoved.indexOf(rightOffset) !== -1) {
218-
removes.push({
219-
from: rightOffset,
220-
left: leftChildren[leftKeys[rightKey]],
221-
right: rightChildren[rightOffset]
222-
});
223-
216+
removes.push({left: rightChildren[rightOffset], right: leftKeys[rightKey]});
224217
rightKey = rightIndex[++rightOffset];
225218
} else if (!rightKey) {
226219
leftKey = leftIndex[++leftOffset];
227220
} else if (!leftKey) {
228221
rightKey = rightIndex[++rightOffset];
229-
} else if (!(leftKey in rightKeys)) {
230-
leftKey = leftIndex[++leftOffset];
231-
} else if (!(rightKey in leftKeys)) {
232-
rightKey = rightIndex[++rightOffset];
233222
} else if (rightKey === leftKey) {
234223
leftKey = leftIndex[++leftOffset];
235224
rightKey = rightIndex[++rightOffset];
225+
} else if (leftKeys[rightKey] - leftOffset >= rightKeys[leftKey] - rightOffset) {
226+
inserts.push({left: rightChildren[rightOffset], right: rightOffset});
227+
leftMoved.push(leftKeys[rightKey]);
228+
rightKey = rightIndex[++rightOffset];
236229
} else {
237-
leftDistance = leftKeys[rightKey] - leftOffset;
238-
rightDistance = rightKeys[leftKey] - rightOffset;
239-
240-
if (leftDistance > rightDistance) {
241-
inserts.push({
242-
to: rightOffset,
243-
left: leftChildren[leftKeys[rightKey]],
244-
right: rightChildren[rightOffset]
245-
});
246-
247-
leftMoved.push(leftKeys[rightKey]);
248-
rightKey = rightIndex[++rightOffset];
249-
} else {
250-
inserts.push({
251-
to: leftOffset,
252-
left: leftChildren[leftOffset],
253-
right: rightChildren[rightKeys[leftKey]]
254-
});
255-
256-
rightMoved.push(rightKeys[leftKey]);
257-
leftKey = leftIndex[++leftOffset];
258-
}
230+
inserts.push({left: leftChildren[leftOffset], right: rightKeys[leftKey]});
231+
rightMoved.push(rightKeys[leftKey]);
232+
leftKey = leftIndex[++leftOffset];
259233
}
260234
}
261235

262236
if (removes.length === 0 && inserts.length === 0) {
263-
return {children: next, moves: null};
237+
return {children: leftChildren, moves: null};
264238
}
265239

266240
return {
267-
children: next,
241+
children: leftChildren,
268242
moves: {removes: removes, inserts: inserts}
269243
};
270244
}
@@ -280,6 +254,11 @@ function keyIndex(children) {
280254

281255
while (++index < length) {
282256
child = children[index];
257+
258+
if (!child) {
259+
continue;
260+
}
261+
283262
key = syntheticKey(child);
284263

285264
if (key in counts) {

readme.md

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -164,13 +164,12 @@ In the diff:
164164
## `MoveDiff`
165165

166166
`MoveDiff` is an object with two arrays: `removes` and `inserts`.
167-
They are never both empty. Objects in `inserts` and `removes` have the
168-
following properties:
167+
They always have equal lengths, and are never both empty. Objects in
168+
`inserts` and `removes` have the following properties:
169169

170-
* `from` (`number`), if in `removes` — Current index of the child in `parent`
171-
* `left` ([`Node`][node]) — Left node
172-
* `right` ([`Node`][node]) — Right node
173-
* `to` (`number`), if in `inserts` — Next index of the child in `parent`
170+
* `left` ([`Node`][node]) — The moved node;
171+
* `right` (`number`) — The index this node moved from (when in `removes`) or
172+
to (when in `inserts`).
174173

175174
## License
176175

test.js

Lines changed: 60 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -563,7 +563,17 @@ test('unist-diff', function (t) {
563563
st.deepEqual(
564564
diff(left, right),
565565
{
566-
0: {type: 'insert', left: null, right: one},
566+
0: [
567+
{type: 'insert', left: null, right: one},
568+
{
569+
type: 'order',
570+
left: left,
571+
right: {
572+
removes: [{left: one, right: 2}],
573+
inserts: [{left: one, right: 0}]
574+
}
575+
}
576+
],
567577
left: left
568578
},
569579
'should return an `insert` if a child is prepended'
@@ -582,7 +592,15 @@ test('unist-diff', function (t) {
582592
{
583593
0: [
584594
{type: 'insert', left: null, right: one},
585-
{type: 'insert', left: null, right: two}
595+
{type: 'insert', left: null, right: two},
596+
{
597+
type: 'order',
598+
left: left,
599+
right: {
600+
removes: [{left: three, right: 0}],
601+
inserts: [{left: three, right: 2}]
602+
}
603+
}
586604
],
587605
left: left
588606
},
@@ -600,7 +618,17 @@ test('unist-diff', function (t) {
600618
st.deepEqual(
601619
diff(left, right),
602620
{
603-
0: {type: 'insert', left: null, right: two},
621+
0: [
622+
{type: 'insert', left: null, right: {type: 'bravo'}},
623+
{
624+
type: 'order',
625+
left: left,
626+
right: {
627+
removes: [{left: two, right: 2}],
628+
inserts: [{left: two, right: 1}]
629+
}
630+
}
631+
],
604632
left: left
605633
},
606634
'should return an `insert` if a child is injected'
@@ -620,7 +648,15 @@ test('unist-diff', function (t) {
620648
{
621649
0: [
622650
{type: 'insert', left: null, right: two},
623-
{type: 'insert', left: null, right: three}
651+
{type: 'insert', left: null, right: three},
652+
{
653+
type: 'order',
654+
left: left,
655+
right: {
656+
removes: [{left: four, right: 1}],
657+
inserts: [{left: four, right: 3}]
658+
}
659+
}
624660
],
625661
left: left
626662
},
@@ -774,8 +810,8 @@ test('unist-diff', function (t) {
774810
type: 'order',
775811
left: left,
776812
right: {
777-
removes: [{from: 2, left: charlie, right: charlie}],
778-
inserts: [{left: charlie, right: charlie, to: 0}]
813+
removes: [{left: charlie, right: 2}],
814+
inserts: [{left: charlie, right: 0}]
779815
}
780816
},
781817
left: left
@@ -798,8 +834,8 @@ test('unist-diff', function (t) {
798834
type: 'order',
799835
left: left,
800836
right: {
801-
removes: [{from: 2, left: alpha, right: alpha}],
802-
inserts: [{left: alpha, right: alpha, to: 0}]
837+
removes: [{left: alpha, right: 0}],
838+
inserts: [{left: alpha, right: 2}]
803839
}
804840
},
805841
left: left
@@ -823,12 +859,12 @@ test('unist-diff', function (t) {
823859
left: left,
824860
right: {
825861
removes: [
826-
{from: 1, left: bravo, right: bravo},
827-
{from: 2, left: alpha, right: alpha}
862+
{left: bravo, right: 1},
863+
{left: charlie, right: 2}
828864
],
829865
inserts: [
830-
{to: 0, left: alpha, right: alpha},
831-
{to: 1, left: bravo, right: bravo}
866+
{left: charlie, right: 0},
867+
{left: bravo, right: 1}
832868
]
833869
}
834870
},
@@ -854,13 +890,13 @@ test('unist-diff', function (t) {
854890
type: 'order',
855891
left: alphaOne,
856892
right: {
857-
inserts: [
858-
{left: bravo, right: bravo, to: 0},
859-
{left: charlie, right: charlie, to: 1}
860-
],
861893
removes: [
862-
{from: 1, left: charlie, right: charlie},
863-
{from: 2, left: bravo, right: bravo}
894+
{left: charlie, right: 1},
895+
{left: delta, right: 2}
896+
],
897+
inserts: [
898+
{left: delta, right: 0},
899+
{left: charlie, right: 1}
864900
]
865901
}
866902
},
@@ -886,13 +922,13 @@ test('unist-diff', function (t) {
886922
type: 'order',
887923
left: alphaOne,
888924
right: {
889-
inserts: [
890-
{left: bravo, right: bravo, to: 0},
891-
{left: charlie, right: charlie, to: 1}
892-
],
893925
removes: [
894-
{from: 1, left: charlie, right: charlie},
895-
{from: 2, left: bravo, right: bravo}
926+
{left: charlie, right: 1},
927+
{left: delta, right: 2}
928+
],
929+
inserts: [
930+
{left: delta, right: 0},
931+
{left: charlie, right: 1}
896932
]
897933
}
898934
},

0 commit comments

Comments
 (0)