Ios 集成:与CloudKit文件系统同步时不必要的往返

Ios 集成:与CloudKit文件系统同步时不必要的往返,ios,ensembles,Ios,Ensembles,我已经将Ensembles v2.5集成到我的应用程序中,我正在使用CloudKit文件系统。如集成文档中所述,通过推送通知自动触发合并 一般来说,同步是可行的,但我的问题是,在通过CloudKit将更改同步到第二台设备后,第二台设备似乎会将新的事务日志上载到CloudKit,从而在第一台设备上触发另一次合并(通过推送通知)。有时在第二台设备上进行另一次合并,导致两次不必要的合并 一个实际的例子: 1) 设备1(iPad)进行了更改 2) 更改会传播到CloudKit 3) 推送通知触发设备2上

我已经将Ensembles v2.5集成到我的应用程序中,我正在使用CloudKit文件系统。如集成文档中所述,通过推送通知自动触发合并

一般来说,同步是可行的,但我的问题是,在通过CloudKit将更改同步到第二台设备后,第二台设备似乎会将新的事务日志上载到CloudKit,从而在第一台设备上触发另一次合并(通过推送通知)。有时在第二台设备上进行另一次合并,导致两次不必要的合并

一个实际的例子:
1) 设备1(iPad)进行了更改
2) 更改会传播到CloudKit
3) 推送通知触发设备2上的合并(iPod Touch)

iPad和iPod Touch现在拥有相同的数据,不应再发生合并,但:

4) iPod Touch创建新的事务日志
5) 推送通知触发iPad上的合并
6) iPad创建新的交易日志
7) 推送通知触发合并iPod Touch

这是设备2(iPod Touch)上的合奏跟踪

我觉得奇怪的是,合奏的轨迹指的是两个商店:
-id为826D4BD2-2ED2-4C3B-9A89-22E3D910EC55-476-000000 FAF9F774C3的一个
-一个id为0B96EB62-03B1-414F-BBA5-3FCBDD2E9CD4-777-000002E26205C2DA

作为参考,以下是我如何设置集成:

_ensemble = [[CDEPersistentStoreEnsemble alloc] initWithEnsembleIdentifier:DM_ENSEMBLE_IDENTIFIER
                                                        persistentStoreURL:storeURL
                                                     managedObjectModelURL:[self _getManagedObjectModelURL]
                                                           cloudFileSystem:_iCloudFileSystem];

非常感谢任何正确方向的帮助/指针。

这是预期的行为,最后一次合并应该非常快。如果您发现它太多,您可以很容易地选择限制由推送通知触发的合并。如果在进行合并后一分钟内出现推送,您可以选择忽略它

每次更改的3次合并不是无操作。他们正在进行重要的会计核算,以确保所有设备最终都具有相同的数据

想想像Git这样的组合。在内部,基本上就是这样。现在,您在一个设备上进行更改,这将触发该设备上的新提交(
S1\u D1
)。然后进行合并,将数据推送到云中

由于推送通知,第二个设备现在合并以获取该数据,并为此创建提交(
M1\u D2
)。这可能包括冲突解决,也可能不包括冲突解决,但这对并发系统很重要。这在Git中相当于合并两个分支,您必须有一个新的提交来在历史中表示这一点

合并(
M1\u D2
)被推送到云中,现在原始设备看到一个新的提交,并且必须执行合并操作才能导入它,尽管它本身不会产生任何新的提交

因此,单次保存需要在原始设备上进行合并,在其他设备上进行合并,然后在原始设备上进行另一次合并,才能完全完成。这就是它在Git这样的系统中以及在集成中的工作方式


请注意,尽管需要3个合并操作,但您可以完全控制它们发生的时间。您可以延迟它们,只要您愿意,或者忽略我提到的某些推送。系统足够聪明,可以在最终合并时(就像Git一样)将其全部解决。

这是预期的行为,最后一次合并应该非常快。如果您发现它太多,您可以很容易地选择限制由推送通知触发的合并。如果在进行合并后一分钟内出现推送,您可以选择忽略它

每次更改的3次合并不是无操作。他们正在进行重要的会计核算,以确保所有设备最终都具有相同的数据

想想像Git这样的组合。在内部,基本上就是这样。现在,您在一个设备上进行更改,这将触发该设备上的新提交(
S1\u D1
)。然后进行合并,将数据推送到云中

由于推送通知,第二个设备现在合并以获取该数据,并为此创建提交(
M1\u D2
)。这可能包括冲突解决,也可能不包括冲突解决,但这对并发系统很重要。这在Git中相当于合并两个分支,您必须有一个新的提交来在历史中表示这一点

合并(
M1\u D2
)被推送到云中,现在原始设备看到一个新的提交,并且必须执行合并操作才能导入它,尽管它本身不会产生任何新的提交

因此,单次保存需要在原始设备上进行合并,在其他设备上进行合并,然后在原始设备上进行另一次合并,才能完全完成。这就是它在Git这样的系统中以及在集成中的工作方式


请注意,尽管需要3个合并操作,但您可以完全控制它们发生的时间。您可以延迟它们,只要您愿意,或者忽略我提到的某些推送。当你最终合并时(就像Git一样),这个系统足够聪明,可以把一切都弄清楚。

Hi Drew,谢谢你的详细回答。这是我最初的想法,但在测试过程中,我被我的观察结果弄糊涂了,有时我看到2个合并,有时3个合并,有时4个合并(就像我上面的例子)。我想这应该归因于另一个问题,我将尝试在一个新问题中描述。嗨,德鲁,谢谢你的详细回答。这是我最初的想法,但在测试过程中,我被我的观察结果弄糊涂了,有时我看到2个合并,有时3个合并,有时4个合并(就像我上面的例子)。我想这应该归因于另一个问题,我将尝试在一个新问题中描述这个问题。
IPOD TOUCH
18:16:28.199 | iCloudSyncActivity | Thread 16 | did receive remote notification, userInfo = '{
    aps =     {
        "content-available" = 1;
        sound = "";
    };
    ck =     {
        ce = 2;
        cid = "iCloud.com.example.app";
        nid = "cc0f33fc-0488-4abb-b9aa-2bfd7c8db88b";
        qry =         {
            dbs = 1;
            fo = 1;
            rid = "CDEFileSystemNode_/DiveMateMainStore/events/33_826D4BD2-2ED2-4C3B-9A89-22E3D910EC55-476-000000FAF9F774C3_21.cdeevent";
            sid = CDEFileAddedSubscription;
            zid = "com.mentalfaculty.ensembles.zone.schema2";
            zoid = "_7fd2f6a37e22282e02a1d8fb52ba2d8e";
        };
    };
}'

IPAD:
18:16:42.258 | iCloudSyncActivity | Thread 15 | did receive remote notification, userInfo = '{
    aps =     {
        "content-available" = 1;
        sound = "";
    };
    ck =     {
        ce = 2;
        cid = "iCloud.com.example.app";
        nid = "2bb1a2f0-5dbb-47b7-b6e1-1e6de9afdac9";
        qry =         {
            dbs = 1;
            fo = 1;
            rid = "CDEFileSystemNode_/DiveMateMainStore/events/34_0B96EB62-03B1-414F-BBA5-3FCBDD2E9CD4-777-000002E26205C2DA_16.cdeevent";
            sid = CDEFileAddedSubscription;
            zid = "com.mentalfaculty.ensembles.zone.schema2";
            zoid = "_7fd2f6a37e22282e02a1d8fb52ba2d8e";
        };
    };
}'

IPOD TOUCH
[260     ] 18:16:48.064 | iCloudSyncActivity | Thread 16 | did receive remote notification, userInfo = '{
    aps =     {
        "content-available" = 1;
        sound = "";
    };
    ck =     {
        ce = 2;
        cid = "iCloud.com.example.app";
        nid = "4ee5383d-9a94-4596-99f2-18ae7da6e0ca";
        qry =         {
            dbs = 1;
            fo = 1;
            rid = "CDEFileSystemNode_/DiveMateMainStore/events/35_826D4BD2-2ED2-4C3B-9A89-22E3D910EC55-476-000000FAF9F774C3_22.cdeevent";
            sid = CDEFileAddedSubscription;
            zid = "com.mentalfaculty.ensembles.zone.schema2";
            zoid = "_7fd2f6a37e22282e02a1d8fb52ba2d8e";
        };
    };
}'
_ensemble = [[CDEPersistentStoreEnsemble alloc] initWithEnsembleIdentifier:DM_ENSEMBLE_IDENTIFIER
                                                        persistentStoreURL:storeURL
                                                     managedObjectModelURL:[self _getManagedObjectModelURL]
                                                           cloudFileSystem:_iCloudFileSystem];