iOS項目iCloud及CloudKit Dashboard運用
CloudKit是蘋果最新推出的基于iCloud的一個云端數據存儲服務.其 主要由下面兩部分組成:
-
一個儀表web頁面,用于管理公開數據的記錄類型.
-
一組API接口,用于iCloud和設備之間的數據傳遞.
一、首先在XCode上面打開關于iCloud功能
1:進入對應的項目Targets 中的Capabilities 選項卡,打開關于iCloud功能;如果勾選iCloud Documents或CloudKit會自動生成一個帶iCloud.開頭的Containers,要配置證書支持;CloudKit Dashboard則可以直接跳轉到Web配置關于iCloud的內容;而關于Steps則是配置的步驟是否都成功;
二、關于證書如何配置支持iCloud功能
1:進入蘋果證書管理后臺中的Identifiers里有個iCloud Containers菜單
因為實例中的Bundle Identifier的名字wjy.com.MobileProject;所以在這邊創建一個iCloud.wjy.com.MobileProject的ID值;都是前面增加一個iCloud為開頭;app的bundle id需要與iCloud容器相對應,iCloud容器名必須是唯一的,因為這是Cloudkit用來訪問數據所使用的全局標識符。由于iCloud容器名包含bundle id,因此bundle id也必須是唯一的(這就是為何需要修改com.raywendrelich.BabiFud)。
為了讓entitlements起作用,需要在App的證書、標識符與配置文件中ID的部分列出app/bundle id。這意味著標識的證書使用了設置的team id與app id,從中可得到iCloud容器的id。若已經在一個可用的開發者賬號中標識了的話Xcode會自動完成這一切。不巧的是,這有時是不同步的,需要更新ID-使用iCloud功能面板修改CloudKit容器ID。否則的話需要修改info.plist文件或BabiFud.entitlements文件來確保id values與所設置的bundle id一致。
2:創建完上面的ID后,同樣進行Identifiers里的App IDs,找到我們當前的App ID然后對它進行編輯
打開 iCloud的功能選擇,并且選擇 Include CloudKit support,這邊這時會有一個警告出現,選擇右邊的 Edit進行編輯
這時會有剛才創建好的那個 iCloud ID可以選擇綁定;選擇好以后外面的警告也會消除;然后生成對應的描述文件安裝后, XCode上面的步驟報錯也會消除;
三、設置iCloud的數據
1:要進入CloudKit Dashboard操作有兩種方式,第一種如上面第一點所說可以直接點CloudKit Dashboard進入,另一種就是進入蘋果賬號后臺也有一個相應的菜單;
2:進入CloudKit Dashboard可以看到如下的頁面
2.1 SCHEMA :
CloudKit容器的高級類:Record Types, Security Roles, 和Subscription Types,其中主要使用的是Record Types;
一個Record Type用來定義一個單獨的記錄(可以理解為一個數據模型),相當于存儲數據的模板,和數據庫的表結構類似;
2.2 PUBLIC DATA 和 PRIVATE DATA
就是你保存數據的地方,開發者可以查看所有的共享數據,但是只能看到自己的私密數據,無法看到用戶的私密數據;這里沒有顯示PRIBATE DATA,其結構和PUBLIC DATA是一樣的;
User Records 記錄一些當前使用者的信息;
Default Zone :這里可以查看數據的詳細信息,也是后面主要使用的;
2.3 ADMIN 主要是管理開發者團隊權限的,這里不做過多介紹;
3:切回Record Type選項,點擊右邊欄的左上角的 "+ ",新增一個模型:
輸入模型名稱: 默認只有一個StringField的屬性(這里暫且這么稱呼吧),可以點擊下面的Add Field... 新增屬性列表;
同樣可以選擇屬性的類型,如下圖:
設置完成后,點擊右下角的 Save按鈕即可保存!這樣,一個模型就建立好了;存儲類型的數據:
1. NSData (single bytes)
2. NSDate (date and time)
3. NSNumber (both Int and Double)
4. NSString (or String in Swift)
5. NSArray (list)
6. CKReference (used to create relationships between objects)
7. CLLocation (location)
8. CKAsset (file)
5:回到Default Zone,中間藍色區域的右上角的名稱旁有個倒三角,這里可以選擇使用(查詢)哪個模型下的數據:
6:如果要存是圖片字段記得選Asset類型
注意: 1 Public Record , 1 Private Record,意思是 :使用模型 Note的有一條公共數據,一條隱私數據,由于我登陸的 iCloud賬號和開發者賬號不一樣,相當于是用戶賬號,所以這里是看不到那個隱私數據的
四、代碼操作iCloud功能
1:首先引入CloudKit.framework系統框架,并引入命名空間#import 就可以進行操作
2:首先是判斷手機中的iCloud功能是否開啟,如下面如果有值則表示已經開啟的iCloud功能;
id cloudUrl=[[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil];
這個方法接受一個參數, 就是要獲取的容器標識。 所謂容器標識, 大多數應用只會用到一個 iCloud 容器,所以我們這里傳入 nil, 就代表默認獲取第一個可用的容器。這個方法內部會查找當前應用擁有的 iCloud 容器, 如果找到就會返回這個容器的 URL, 證明當前應用的 iCloud 容器可用。 如果找不到,就會返回 nil, 證明當前應用的 iCloud 不可用。
注意: iCloud 容器和你 App 文件沙盒, 在 iOS 文件系統中其實是分別存放在兩個不同的地方的:
iCloud 文件路徑格式 file:///private/var/mobile/Library/Mobile%20Documents/iCloud~com~xxx~aaa/Documents
App 沙盒文件路徑格式 file:///var/mobile/Containers/Data/Application/3B4376B3-89B5-3342-8057-3450D4224518/Documents/
由此可見, 這也是為什么 iCloud 和 Sandbox 文件路徑訪問需要兩套不同的方式的原因了。
3:增加一條記錄,可以給它一個固定的recordID,就像數據表的主鍵一樣,查找、更新跟刪除有用;
-(void)addCloudDataWithPublic:(BOOL)isPublic recordID:(NSString *)recordID name:(NSString *)name password:(NSString *)password
{
//CloudKit給應用程序分配部分空間,用于存儲數據,首先要獲取這個存儲空間,這里我們直接獲取了默認的存儲器(可以自定義存儲器):
CKContainer *container=[CKContainer defaultContainer];
CKDatabase *database;
if (isPublic) {
database=container.publicCloudDatabase; //公共數據
}
else
{
database=container.privateCloudDatabase;//隱藏數據
}
//創建主鍵ID 這個ID可以到時查找有用到
CKRecordID *noteId=[[CKRecordID alloc]initWithRecordName:recordID];
//創建CKRecord 保存數據
CKRecord *noteRecord = [[CKRecord alloc]initWithRecordType:@"User" recordID:noteId];
//設置數據
[noteRecord setObject:name forKey:@"name"];
[noteRecord setObject:password forKey:@"password"];
//保存操作
[database saveRecord:noteRecord completionHandler:^(CKRecord * _Nullable record, NSError * _Nullable error) {
if (!error) {
[self showAlertMessage:@"保存成功"];
}
}];
}
4 :假如要保存帶有圖片的字段,需要用到 CKAsset ,他的初始化需要一個 URL ,所以這里,我先把圖片數據保存到本地沙盒,生成一個 URL ,然后再去創建 CKAsset:
//增加帶圖片的提交 圖片的保存,需要用到CKAsset,他的初始化需要一個URL,所以這里,我先把圖片數據保存到本地沙盒,生成一個URL,然后再去創建CKAsset:
-(void)saveImageDataWithPublic:(BOOL)isPublic recordID:(NSString *)recordID name:(NSString *)name password:(NSString *)password
{
//保存圖片 圖片的保存,需要用到CKAsset,他的初始化需要一個URL,所以這里,我先把圖片數據保存到本地沙盒,生成一個URL,然后再去創建CKAsset:
UIImage *image=[UIImage imageNamed:@"icloudImage"];
NSData *imageData = UIImagePNGRepresentation(image);
if (imageData == nil) {
imageData = UIImageJPEGRepresentation(image, 0.6);
}
NSString *tempPath = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents/imagesTemp"];
NSFileManager *manager = [NSFileManager defaultManager];
if (![manager fileExistsAtPath:tempPath]) {
[manager createDirectoryAtPath:tempPath withIntermediateDirectories:YES attributes:nil error:nil];
}
NSString *filePath = [NSString stringWithFormat:@"%@/%@",tempPath,@"iCloudImage"];
NSURL *url = [NSURL fileURLWithPath:filePath];
[imageData writeToURL:url atomically:YES];
CKAsset *asset = [[CKAsset alloc]initWithFileURL:url];
//與iCloud進行交互
CKContainer *container=[CKContainer defaultContainer];
CKDatabase *database;
if (isPublic) {
database=container.publicCloudDatabase; //公共數據
}
else
{
database=container.privateCloudDatabase;//隱藏數據
}
//創建主鍵ID 這個ID可以到時查找有用到
CKRecordID *noteId=[[CKRecordID alloc]initWithRecordName:recordID];
//創建CKRecord 保存數據
CKRecord *noteRecord = [[CKRecord alloc]initWithRecordType:@"User" recordID:noteId];
//設置數據
[noteRecord setObject:name forKey:@"name"];
[noteRecord setObject:password forKey:@"password"];
[noteRecord setObject:asset forKey:@"userImage"];
//保存操作
[database saveRecord:noteRecord completionHandler:^(CKRecord * _Nullable record, NSError * _Nullable error) {
if (!error) {
[self showAlertMessage:@"保存成功"];
}
}];
}
其它修改、查找、刪除的代碼可以直接見下面的源代碼地址;
五、操作實例
編寫一個關于在同一臺手機上免登錄的實例,主要原理是通過獲取手機設備唯一碼,然后通過iCloud保存到云端,在刪除APP后再安裝后就可以直接從云端獲得用戶跟密碼;會不斷完善此實例,如果感興趣可以點星并關注,會接著編寫關于iCloud關于文件的同步功能;注意證書可以換成自個的,步驟如上:
來自:http://www.cocoachina.com/ios/20161026/17786.html