Beginning with CloudKit

Là một lập trình viên iOS, có những lúc bạn muốn viết một ứng dụng đơn giản, lấy dữ liệu từ server trả về và hiển thị lên màn hình ứng dụng. Server đó chỉ cần truy xuất 1 vài dữ liệu có sẵn trên đó, lọc, sắp xếp ..., cho phép người dùng upload dữ liệu lên trên đó. Phần việc ở client là quá đơn giản, nhưng việc tạo ra 1 server để đáp ứng công việc đơn giản đó thì không phải iOS Developer nào cũng có thể làm được. Có 1 số BaaS (Back end as a Service) có thể làm thay điều đó cho chúng ta. Và ở iOS8, Apple cung cấp thêm cho chúng ta 1 BaaS mới là CloudKit (https://developer.apple.com/icloud/) cloudkit-featured-1024x674.png

Câu hỏi đầu tiên được đặt ra là tại sao lại là CloudKit mà không phải những dịch vụ khác. Câu trả lời là : Đơn giản, tin cậy và chi phí

  • Đơn giản : Với CloudKit, cái mà đã được Apple xây dựng sẵn, công việc của bạn gần như chỉ là nhập dữ liệu mà thôi.
  • Tin cậy : rõ ràng, với người dùng và lập trình viên iOS, việc bảo mật, sự chuyên nghiệp trong công việc của Apple luôn được nhắc đến như một điều hin nhiên, không có gì phải bàn cãi
  • Chi phí : Bạn có thể tham khảo thêm chi phí ở đây (https://developer.apple.com/icloud/). Mức giá mà Apple đưa ra không phải là thấp (từ trước tới giờ vẫn luôn là thế) nhưng cần phải biết thêm rằng ứng dụng sử dụng CloudKit có thể lợi dụng iCloud Storage của người dùng thay vì lưu tất cả lên server của mình

Dưới đây sẽ là 1 ứng dụng nhỏ giúp các bạn có thể làm quen với CloudKit (link source code https://github.com/quocnb/SharingWifiPass)

1. Kích hoạt CloudKit

Trên Project, vào phần Project Setting > Capabilities > Switch iCloud to On > Tick CloudKit

Screen Shot 2015-09-25 at 5.47.50 PM.png

Lưu ý : Để kích hoạt CloudKit, bạn phải là Developer Member, cái mà mỗi năm bạn phải trả 99$ để có thể upload app lên Appstore.

Sau khi kích hoạt CloudKit thành công, Apple sẽ tự động tạo cho bạn CloudKit Dashboard để quản lý ứng dụng. Bạn có thể truy cập vào nó qua việc bấm vào button CloudKit Dashboard. Dashboard là nơi mà chúng ta sẽ cấu hình server của mình

2. Cấu hình server

Trên Dashboard, Record Types, tạo bản ghi Screen Shot 2015-09-25 at 9.22.39 AM.png

Các kiểu dữ liệu Screen Shot 2015-09-25 at 6.09.09 PM.png

Thêm một vài dữ liệu mẫu vào qua phần Public Data > Default Zone

Screen Shot 2015-09-25 at 5.00.42 PM.png

Vậy là xong, việc cấu hình server quá đơn giản phải không, đúng như tiêu chí ban đầu của CloudKit. 😃

3. Lấy dữ liệu ở client

Một điều đặc biệt là việc giao tiếp với Cloud server hoàn toàn được đóng kín và chúng ta chỉ giao tiếp với server thông qua một module được cung cấp sẵn của Apple là CloudKit.

Khai báo và khởi tạo database

let container : CKContainer
let publicDB : CKDatabase
let privateDB : CKDatabase
init() {
	container = CKContainer.defaultContainer()
	publicDB = container.publicCloudDatabase // Public Data
	privateDB = container.privateCloudDatabase // Private Data
}

Request tới db để lấy dữ liệu trả về

let fetchedAllPredicate : NSPredicate = NSPredicate(format:
                "TRUEPREDICATE") // Load All Record
//let predicate : NSPredicate = NSPredicate(format: "distanceToLocation:fromLocation:(%K,%@) < %f","Location", location!, radiusSearch) // Load near by wifi
let query : CKQuery = CKQuery(recordType: RecordType, predicate: predicate)
db.performQuery(query, inZoneWithID: nil) { (results : [CKRecord]?, error : NSError?) -> Void in
   if error != nil {
       // xử lý error ở đây
   } else {
      // xử lý dữ liệu trả về ở đây
   }
}

Vậy là đã xử lý xong phần lấy thông tin trên server. Tùy thuộc vào từng loại dữ liệu đã tạo sẵn trên server để chúng ta có thể parse ra swift object. Từng loại object tương ứng sẽ được parse sang qua đoạn code dưới đây

// String
let string : String = record.objectForKey("StringKey") as! String
// Int
let int : Int = (record.objectForKey("IntKey") as! NSNumber).integerValue
//Location
let location : CLLocation = record.objectForKey("LocationKey") as! CLLocation
// Photo (Asset Type)
dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0)){
	let coverPhoto = self.record.objectForKey("CoverPhoto") as CKAsset!
	if let asset = coverPhoto {
		if let url = asset.fileURL {
			let imageData = NSData(contentsOfFile: url.path!)
		}
	}
}

Screen Shot 2015-09-26 at 2.20.41 PM.png Screen Shot 2015-09-26 at 2.20.46 PM.png

** 4. Add và update dữ liệu lên server **

Việc add và update dữ liệu lên cloud, đều thông qua 1 hàm là

// Add case
record = CKRecord(recordType: RecordType)
// Edit case
record // Do nothing
// Create new value for record by
record!.setObject(object, forKey: "KeyInCloud")
// Note : Object must be type : NSString, NSArray, NSNumber, NSDate, NSData, CKReference, CKAsset, CLLocation

database.saveRecord(record!, completionHandler: { (record : CKRecord?, error : NSError?) -> Void in
	if error != nil {
        // Handle error
	} else {
		// Save or update success

	})
}

Reload lại dữ liệu, ta sẽ thấy dữ liệu đã được update Screen Shot 2015-09-26 at 3.24.24 PM.png

Screen Shot 2015-09-26 at 3.24.30 PM.png

** 5. Private vs public database **

Screen Shot 2015-09-25 at 6.21.33 PM.png

Như đã giới thiệu ở trên. CloudKit cho phép người dùng lưu dữ liệu lên CloudKit của chính họ - cái mà được gọi là Private Database. Việc request, add, edit ở private database cũng tương tự như Public Database. Trái ngược với Public Database, dữ liệu trên Private Database sẽ được giấu kín hoàn toàn và chỉ có chủ tài khoản iCloud đó mới có thể lấy được dữ liệu từ đó. Việc này cho phép lập trình viên có thể giảm thiểu được dữ liệu lưu trên public server, cũng như số lượng request đến nó, giúp giảm tối đa chi phí cho người phát triển ứng dụng.

** 6. CloudKit vs CoreData + iCloud **

  • Sử dụng CoreData với iCloud sẽ giúp bạn đồng bộ hóa dữ liệu từ client lên cloud hay download từ cloud về client một cách hoàn toàn tự động. Nếu hoạt động trong chế độ offline, dữ liệu dưới client vẫn có thể sử dụng hoàn toàn bình thường, và khi có mạng trở lại, việc đồng bộ sẽ lại được thực hiện hoàn toàn tự động
  • CloudKit thì hoàn toàn khác. Nó là một hệ thống truyền dữ liệu, mọi thao tác đều không thể thực hiện tự động, bạn cần viết code để get, update hay add dữ liệu. Nếu không có internet, mọi việc sẽ không thể thực hiện được.

** 7. Tổng kết **

Với CloudKit, bạn có thể dễ dàng tạo ra 1 server để phục vụ cho ứng dụng của mình. Việc cấu hình server và giao tiếp với server rất dễ dàng mà vẫn đảm bảo tính bảo mật của dữ liệu. Tuy nhiên CloudKit cũng có 1 số nhược điểm là nó bị đóng kín với iOS và MacOS, nên việc cross platform là bất khả thi. Hơn thế nữa, việc sử dụng Public Database cũng khá hạn chế với storage giới hạn của CloudKit. Nên khi sử dụng nó, hãy cân nhắc kỹ những điều này


All Rights Reserved