如何(以及何时)在CKRecord上使用iCloud的encodeSystemFields方法? [英] How (and when) do I use iCloud's encodeSystemFields method on CKRecord?

查看:93
本文介绍了如何(以及何时)在CKRecord上使用iCloud的encodeSystemFields方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

encodeSystemFields

导出后该数据,反序列化时我必须做些特别的事情吗?

Once I export that data, must I do anything special when de-serializing it?

我应该对数据中的信息采取什么方案?

What scenarios should I act upon information in that data?

作为变体(如果不在本指南中涵盖)上一个问题),这些信息可以帮助我预防什么? (我认为是数据损坏)

As a variation (and if not covered in the previous question), what does this information help me guard against? (data corruption I assume)

推荐答案

encodeSystemFields对于避免必须再次从CloudKit获取CKRecord进行更新(禁止记录)很有用。

encodeSystemFields is useful to avoid having to fetch a CKRecord from CloudKit again to update it (barring record conflicts).

这个想法是:

在存储从CloudKit检索到的记录的数据时(对于例如,通过 CKFetchRecordZoneChangesOperation 检索以将记录更改同步到本地存储):

When you are storing the data for a record retrieved from CloudKit (for example, retrieved via CKFetchRecordZoneChangesOperation to sync record changes to a local store):

1。)将CKRecord存档到NSData:

1.) Archive the CKRecord to NSData:

let record = ...

// archive CKRecord to NSData
let archivedData = NSMutableData()
let archiver = NSKeyedArchiver(forWritingWithMutableData: archivedData)
archiver.requiresSecureCoding = true
record.encodeSystemFieldsWithCoder(with: archiver)
archiver.finishEncoding()

2。)将archivedData本地存储(例如,在您的数据库中) )与您的本地记录相关联。

2.) Store the archivedData locally (for example, in your database) associated with your local record.

当您要将对本地记录所做的更改保存回CloudKit 时:

1。)从存储的NSData中取消CKRecord的存储:

1.) Unarchive the CKRecord from the NSData you stored:

let archivedData = ... // TODO: retrieved from your local store

// unarchive CKRecord from NSData
let unarchiver = NSKeyedUnarchiver(forReadingWithData: archivedData)  
unarchiver.requiresSecureCoding = true 
let record = CKRecord(coder: unarchiver)

2。)使用该未归档的记录作为更改的基础。 (即在其上设置更改后的值)

2.) Use that unarchived record as the base for your changes. (i.e. set the changed values on it)

record["City"] = "newCity"

3。)通过CKModifyRecordsOperation将记录保存到CloudKit。

3.) Save the record(s) to CloudKit, via CKModifyRecordsOperation.

从Apple:


本地存储记录

Storing Records Locally

如果将记录存储在本地数据库中,请使用encodeSystemFields(with :)方法对记录的元数据进行编码和存储。 元数据包含记录ID和更改标记,稍后需要这些记录ID和更改标记才能将本地数据库中的记录与CloudKit存储的记录进行同步。

If you store records in a local database, use the encodeSystemFields(with:) method to encode and store the record’s metadata. The metadata contains the record ID and change tag which is needed later to sync records in a local database with those stored by CloudKit.

在CloudKit中将更改保存到CKRecord时,需要将更改保存到服务器记录

When you save changes to a CKRecord in CloudKit, you need to save the changes to the server's record.

您不能只创建新的CKRecord使用相同的recordID,在其上设置值并保存。如果这样做,将会收到服务器记录已更改的消息。错误-在这种情况下,是因为现有的服务器记录包含您的本地记录(从头创建)丢失的元数据。

You can't just create a new CKRecord with the same recordID, set the values on it, and save it. If you do, you'll receive a "Server Record Changed" error - which, in this case, is because the existing server record contains metadata that your local record (created from scratch) is missing.

因此,您有两种选择来解决此问题:

So you have two options to solve this:


  1. 从CloudKit请求CKRecord(使用recordID),对该CKRecord进行更改,然后将其保存回CloudKit。

  1. Request the CKRecord from CloudKit (using the recordID), make changes to that CKRecord, then save it back to CloudKit.

使用 encodeSystemFields ,并将元数据存储在本地,将其取消存档以创建基础目录。 CKRecord具有所有适当的元数据,可以将对CKRecord的更改保存回CloudKit。

Use encodeSystemFields, and store the metadata locally, unarchiving it to create a "base" CKRecord that has all the appropriate metadata for saving changes to said CKRecord back to CloudKit.

#2可以节省您的网络访问时间-trips *。

#2 saves you network round-trips*.

*同时,假设另一台设备没有修改记录,这也是您可以防止的数据。如果另一设备在您上次检索该记录与尝试保存该记录之间修改了记录,则CloudKit将(默认)拒绝您的记录保存尝试,并带有服务器记录已更改。这是您以适合您的应用程序和数据模型的方式执行冲突解决的线索。 (通常,通过从CloudKit中获取新的服务器记录,然后在再次尝试保存之前,对该CKRecord重新应用适当的值更改。)

*Assuming another device hasn't modified the record in the meantime - which is also what this data helps you guard against. If another device modifies the record between the time you last retrieved it and the time you try to save it, CloudKit will (by default) reject your record save attempt with "Server Record Changed". This is your clue to perform conflict resolution in the way that is appropriate for your app and data model. (Often, by fetching the new server record from CloudKit and re-applying appropriate value changes to that CKRecord before attempting the save again.)

注意:任何时候在将更新的CKRecord保存到CloudKit或从CloudKit中获取更新的CKRecord之前,必须记住要更新本地存储的已归档CKRecord。

NOTE: Any time you save/retrieve an updated CKRecord to/from CloudKit, you must remember to update your locally-stored archived CKRecord.

这篇关于如何(以及何时)在CKRecord上使用iCloud的encodeSystemFields方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆