-
Notifications
You must be signed in to change notification settings - Fork 5
Different result with batched parameter when one list is empty #7
Copy link
Copy link
Open
Description
When performing diff between two lists where the compared list is empty results with different results depending on the batched parameter. To simplify the problem I've created a sample code so that it can be easily tested.
import 'package:diffutil_dart/diffutil.dart';
import 'package:flutter_test/flutter_test.dart';
void main() {
test("empty -> [...6 items] should have 6 inserts operations with consecutive positions and count 1 when not batched", () {
final apiList = [
SimpleClass("1", "Content 1"),
SimpleClass("2", "Content 2"),
SimpleClass("3", "Content 3"),
SimpleClass("4", "Content 4"),
SimpleClass("5", "Content 5"),
SimpleClass("6", "Content 6"),
];
final dbList = <SimpleClass>[];
final diff = calculateDiff(
SimpleClassDiffDelegate(dbList, apiList),
detectMoves: true,
).getUpdates(batch: false).toList();
expect(diff, const [
Insert(position: 0, count: 1),
Insert(position: 1, count: 1),
Insert(position: 2, count: 1),
Insert(position: 3, count: 1),
Insert(position: 4, count: 1),
Insert(position: 5, count: 1),
]);
});
test("empty -> [...6 items] should have 1 insert operation with count 6 on position 0 when batched", () {
final apiList = [
SimpleClass("1", "Content 1"),
SimpleClass("2", "Content 2"),
SimpleClass("3", "Content 3"),
SimpleClass("4", "Content 4"),
SimpleClass("5", "Content 5"),
SimpleClass("6", "Content 6"),
];
final dbList = <SimpleClass>[];
final diff = calculateDiff(
SimpleClassDiffDelegate(dbList, apiList),
detectMoves: true,
).getUpdates(batch: true).toList();
expect(diff, const [
Insert(position: 0, count: 6),
]);
});
test("[...6 items] -> empty list should have 6 remove operations with 6 consecutive positions and count 1 when not batched", () {
final apiList = <SimpleClass>[];
final dbList = [
SimpleClass("1", "Content 1"),
SimpleClass("2", "Content 2"),
SimpleClass("3", "Content 3"),
SimpleClass("4", "Content 4"),
SimpleClass("5", "Content 5"),
SimpleClass("6", "Content 6"),
];
final diff = calculateDiff(
SimpleClassDiffDelegate(dbList, apiList),
detectMoves: true,
).getUpdates(batch: false).toList();
expect(diff, const [
Remove(position: 5, count: 1),
Remove(position: 4, count: 1),
Remove(position: 3, count: 1),
Remove(position: 2, count: 1),
Remove(position: 1, count: 1),
Remove(position: 0, count: 1),
]);
});
test("[...6 items] -> empty list should have 1 remove operation with position 0 and count 6 when batched", () {
final apiList = <SimpleClass>[];
final dbList = [
SimpleClass("1", "Content 1"),
SimpleClass("2", "Content 2"),
SimpleClass("3", "Content 3"),
SimpleClass("4", "Content 4"),
SimpleClass("5", "Content 5"),
SimpleClass("6", "Content 6"),
];
final diff = calculateDiff(
SimpleClassDiffDelegate(dbList, apiList),
detectMoves: true,
).getUpdates(batch: true).toList();
expect(diff, const [
Remove(position: 0, count: 6),
]);
});
}
class SimpleClass {
final String id;
final String content;
SimpleClass(this.id, this.content);
@override
bool operator ==(Object other) =>
identical(this, other) ||
other is SimpleClass &&
runtimeType == other.runtimeType &&
id == other.id &&
content == other.content;
@override
int get hashCode => id.hashCode ^ content.hashCode;
}
class SimpleClassDiffDelegate implements DiffDelegate {
final List<SimpleClass> _oldList;
final List<SimpleClass> _newList;
SimpleClassDiffDelegate(this._oldList, this._newList);
@override
bool areContentsTheSame(int oldItemPosition, int newItemPosition) => _oldList[oldItemPosition] == _newList[newItemPosition];
@override
bool areItemsTheSame(int oldItemPosition, int newItemPosition) => _oldList[oldItemPosition].id == _newList[newItemPosition].id;
@override
Object getChangePayload(int oldItemPosition, int newItemPosition) => _newList[newItemPosition];
@override
int getNewListSize() => _newList.length;
@override
int getOldListSize() => _oldList.length;
}In the first test the result is:
Expected: [
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 1, count: 1},
Insert:Insert{position: 2, count: 1},
Insert:Insert{position: 3, count: 1},
Insert:Insert{position: 4, count: 1},
Insert:Insert{position: 5, count: 1}
]
Actual: [
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 0, count: 1},
Insert:Insert{position: 0, count: 1}
]
Which: at location [1] is Insert:<Insert{position: 0, count: 1}> instead of Insert:<Insert{position: 1, count: 1}>
I think that we should obtain the result as in the test case, so that we can easily create a list of all items added.
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
No labels