Skip to content

Commit 423ba15

Browse files
beaucollinsroundhill
authored andcommitted
When a merge fails, queue the object to be synced again (#203)
* When a merge fails, queue the object to be synced again * Throw a JSONException if diff match patch didn't apply the patches correctly. * Don't update the object when we encounter an error merging local modifications. * Revert "When a merge fails, queue the object to be synced again" This reverts commit 1b83001. * Adding test for invalid transform exception.
1 parent 877d4e7 commit 423ba15

File tree

3 files changed

+35
-7
lines changed

3 files changed

+35
-7
lines changed

Simperium/src/androidTestSupport/java/com/simperium/JSONDiffTest.java

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -338,6 +338,24 @@ public void testTransformStringDiff()
338338

339339
}
340340

341+
public void testInvalidStringTransformThrowsException()
342+
throws Exception {
343+
String origin = "Line 1\nLine 2\nReplace me";
344+
try
345+
{
346+
JSONObject transformed = JSONDiff.transform(
347+
"=14\t+Before%0A\t=10\t+%0AAfter",
348+
"=14\t-10\t+BYE",
349+
origin
350+
);
351+
fail("Patch transform should have failed.");
352+
}
353+
catch(Exception e)
354+
{
355+
// Test passed
356+
}
357+
}
358+
341359
public void testTransformObjectDiffChangeRemovedKey()
342360
throws Exception {
343361

Simperium/src/main/java/com/simperium/client/Bucket.java

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -927,6 +927,7 @@ public Ghost applyRemoteChange(RemoteChange change)
927927
try {
928928
T object;
929929
Boolean isNew;
930+
Boolean shouldUpdateObject = true;
930931

931932
if (change.isAddOperation()) {
932933
object = newObject(change.getKey());
@@ -962,7 +963,6 @@ public Ghost applyRemoteChange(RemoteChange change)
962963
mSchema.updateWithDefaults(object, updatedProperties);
963964
addObject(object);
964965
} else {
965-
966966
if (localModifications != null && localModifications.length() > 0) {
967967
try {
968968
JSONObject incomingDiff = change.getPatch();
@@ -971,15 +971,17 @@ public Ghost applyRemoteChange(RemoteChange change)
971971
JSONObject transformedDiff = JSONDiff.transform(localDiff, incomingDiff, currentProperties);
972972

973973
updatedProperties = JSONDiff.apply(updatedProperties, transformedDiff);
974-
975974
} catch (JSONException | IllegalArgumentException e) {
976-
// could not transform properties
977-
// continue with updated properties
975+
// We couldn't merge the local and remote changes.
976+
// Hold off on updating the object so that the local change can sync
977+
shouldUpdateObject = false;
978978
}
979979
}
980980

981-
mSchema.update(object, updatedProperties);
982-
updateObject(object);
981+
if (shouldUpdateObject) {
982+
mSchema.update(object, updatedProperties);
983+
updateObject(object);
984+
}
983985
}
984986

985987
} catch(SimperiumException e) {

Simperium/src/main/java/com/simperium/util/JSONDiff.java

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,8 +43,16 @@ public static JSONObject transform(String o_diff, String diff, String source)
4343
LinkedList<Patch> patches = dmp.patch_make(source, dmp.diff_fromDelta(source, diff));
4444

4545
String text = (String) dmp.patch_apply(patches, source)[0];
46-
String combined = (String) dmp.patch_apply(o_patches, text)[0];
4746

47+
Object[] appliedPatch = dmp.patch_apply(o_patches, text);
48+
boolean[] results = (boolean[]) appliedPatch[1];
49+
for (boolean result : results) {
50+
if (!result) {
51+
throw new JSONException("Could not cleanly transform patch.");
52+
}
53+
}
54+
55+
String combined = (String)appliedPatch[0];
4856
if (text.equals(combined)) {
4957
// text is the same, return empty diff
5058
return transformed;

0 commit comments

Comments
 (0)