Arbeta med iCloud Key-Value Storage

Att hålla applikationsdata synkroniserad över enheter är en komplex och skrämmande uppgift. Lyckligtvis är det precis därför Apple byggde iCloud. I denna Tuts + Premium-serie kommer du att lära dig hur iCloud fungerar och hur dina applikationer kan dela data på flera enheter sömlöst.


Finns även i serien:

  1. Arbeta med iCloud: Introduktion
  2. Arbeta med iCloud: Key-Value Storage
  3. Arbetar med iCloud: Dokumentlagring
  4. Arbetar med iCloud: Core Data Integration

I den första delen av denna serie gav jag en introduktion till iCloud och inriktades särskilt på iCloud Storage. Två typer av iCloud Storage är avaiala till utvecklare, Key-Value Storage och Dokumentlagring. Key-Value Storage ligger i fokus för denna handledning.

Vi börjar denna handledning genom att titta närmare på processen med att skapa en applikation för användning med iCloud. Med vår applikation korrekt konfigurerad kommer vi att använda sig av iClouds nyckelvärdeslagring för att hålla vår applikations data synkroniserad på flera enheter.


Innan vi börjar

Vi kan inte testa datasynkronisering med bara en enhet. För att slutföra denna handledning måste du ha minst två iOS-enheter som kör iOS 5 eller högre. Tyvärr kan iOS-simulatorn inte användas för att testa iCloud Storage.

Programmet vi ska bygga kommer att vara ett enkelt iOS-program, vilket innebär att du kan köra den på alla iPhone, iPod Touch eller iPad som kör iOS 5 eller högre. Att läsa denna handledning är fortfarande värt att göra, även om du inte har två separata iOS-enheter som kan användas för testning. Det kommer att lära dig hur iCloud är uppbyggd och hur du kan använda iClouds nyckelvärdeslagring för att förbättra dina egna applikationer.


Steg 1: Projektinställningar

Jag börjar med att gå igenom processen med att konfigurera vår applikation för att använda iCloud Storage. Vi behöver dock först skapa vårt Xcode-projekt.

Skapa ett nytt projekt i Xcode genom att välja Enkel visningsprogram mall. Namn på din ansökan Molnig, ange a företagsidentifierare, uppsättning iPhone för enhetsfamiljen och kontrollera Använd automatisk referensräkning. Återstående kryssrutor ska vara avmarkerade. Berätta Xcode där du vill spara ditt projekt och träffa Skapa.



Det är nyckeln att du noggrant väljer produktnamn och företagsidentifierare för detta projekt. Kombinationen av dessa två element utgörs av buntidentifierare (tillsammans med buntfrasidentifieraren) för din ansökan, vilken iCloud kommer att använda för att unikt identifiera din ansökan. Kontrollera noggrant din stavning, eftersom paketidentifieraren är skiftlägeskänslig.


Steg 2: Ställa in iCloud

Som jag nämnde i den första artikeln i denna Tuts + Premium-serie är det enkelt att ställa in en applikation för att använda iCloud och innebär bara två steg. Låt mig gå igenom processen steg för steg.

Steg 2A: Leveransportal

Öppna din favoritwebbläsare och gå över till Apples iOS Dev Center. Logga in på ditt iOS-utvecklarkonto och klicka på IOS Provisioning Portal länk till höger.


Först måste vi skapa en App ID för vår ansökan. Öppna App-ID fliken till vänster och klicka på Nytt app-ID knappen längst upp till höger. Ge ditt app-ID ett beskrivande namn för att enkelt identifiera det senare. Ange sedan buntidentifieraren jag pratade om för några minuter sedan. Buntidentifieraren är kombinationen av din företagsidentifierare, com.mobiletuts i vårt exempel och produktnamnet, Molnig i vårt exempel. Du kan lämna buntens fröidentifierare inställd på Använd Team ID, vilket är bra för vår ansökan.

Dubbelkontrollera att din buntidentifierare är stavad korrekt. Som jag nämnde tidigare är skräpidentifieringen skiftlägeskänslig. Klicka på Skicka-knappen för att skapa ditt App-ID.


Ditt nyskapade app-ID ska nu vara närvarande i listan med App-ID. Du kommer märka att iCloud är avstängt som standard för varje nyskapat App ID. Låt oss ändra det. Till höger om ditt App-ID klickar du på konfigurera knapp. Nederst på sidan bör du se en kryssruta som säger Aktivera för iCloud. Markera kryssrutan och klicka på Gjort. Vårt App ID är nu konfigurerat för att fungera med iCloud. Det finns en sak vi måste ta hand om när vi är i Provisioning Portal.



För att säkerställa att vår applikation kan köras på våra enheter måste vi skapa en provisioningprofil. Fortfarande i IOS Provisioning Portal, öppna Provisioning fliken till vänster och välj Utveckling fliken längst upp. Klicka på Ny profil knappen längst upp till höger och ange ett beskrivande namn för din nya profil. Välj sedan det utvecklingscertifikat som du vill att profilen ska associeras med och välj det korrekta app-idet från rullgardinsmenyn. Välj slutligen de enheter du ska använda för att testa från listan längst ner på sidan.


När du har klickat på Skicka-knappen längst ned till höger kommer du att märka att din provisioning-profil har status för Avvaktan. Efter att ha laddat om sidan ska profilens status ha uppdaterats till Aktiva. Klicka på nedladdningsknappen bredvid din provisioningprofil och dubbelklicka på profilen. Xcode installerar automatiskt profilen för dig.



Steg 2B: Rättegångar

Många utvecklare cringe när de hör ordet rättigheter. Rättigheterna är inget att vara rädd för när du förstår vad de är för. Rättigheterna ger särskilda förmågor eller säkerhetsbehörigheter till en ansökan. Det är allt som finns där. Det är en enkel lista över nyckelvärdespar som berättar operativsystemet vad din ansökan kan och inte kan göra, och vilka applikationer som har åtkomst till programmets data. Det senare är särskilt viktigt när man arbetar med iCloud.

I vårt exempel tillåter vi iCloud-rättigheter att aktivera iCloud Storage för vår ansökan. För att konfigurera rättigheterna för vår ansökan går vi över till Xcodes målredigerare.

Klicka på vårt projekt i Project Navigator och välj vårt mål från mållistan. Med Sammanfattning fliken vald, bör du se en rubrik som heter ersättningar på botten. Markera den första kryssrutan för att aktivera rättigheter för vår ansökan. Det här alternativet skapar en rättighetsfil för vår ansökan. Textfältet under kryssrutan ska fyllas i för dig. Vi har nu möjlighet att aktivera iCloud Key-Value Storage och iCloud Document Storage.


I den här handledningen kommer jag bara att prata om iCloud Key-Value Storage, markera kryssrutan bredvid iCloud Key Value Store. Igen förfyller Xcode textfältet bredvid kryssrutan med din programbuntidentifierare (utan buntens fröidentifierare). Verifiera att den här paketidentifieraren motsvarar den du angav i provisioneringsportalen när du skapade ditt app-ID. Jag kommer att prata om iCloud Containers i nästa handledning som de relaterar till iCloud Document Storage.

I nedre delen av rättighetsavsnittet ser du nyckelringstillträdesgrupper. I denna lista anges vilka applikationer som har tillgång till dina nyckelordstämplar. Du kan lämna den sektionen orörda för nu.

Innan vi får våra händer smutsiga med iCloud API, måste vi konfigurera våra byggnadsinställningar. Fortfarande i Xcodes målredigerare väljer du Bygg inställningar fliken och rulla ner till Kodsignering sektion. Ange kodsigneringsidentitet för debug och Släpp konfigurationer som matchar profilen som vi just skapat i IOS Provisioning Portal.



Steg 3: Användargränssnitt

Denna handledning är något avancerad och jag antar därför att du är bekant med de grundläggande begreppen iOS-utveckling. Det betyder att jag kommer att flytta lite snabbare än jag brukar göra eftersom vi har mycket att täcka.

Applikationen som vi ska bygga kommer att vara en enkel bokmärkeschef. Vi kan lägga till och ta bort bokmärken, och våra bokmärken synkroniseras över våra enheter. Hur coolt är inte det? Låt oss börja.

Öppna vår huvudkontrollens huvudfiler och skapa en instansvariabel (ivar) av typen NSMutableArray med ett namn på bokmärken. Ivar kommer att lagra våra bokmärken. Bokmärkenna visas i en tabellvy. Skapa ett uttag för tabellvyn i vår bildledarens huvudfiler och se till att vi överensstämmer med vår visningskontroller i tabellvynets datakälla och delegera protokoll. Glöm inte att syntetisera accessorer för båda egenskaperna i vår bildskärmshanterings implementeringsfil. Lägg sedan till två åtgärder till ViewController.h, editBookmarks: och Lägg till bokmärke:. Redo? Gå över till ViewController.xib fil för att koppla upp allting.

 #importera  @interface ViewController: UIViewController  NSMutableArray * _bookmarks; __weak UITableView * _tableView;  @property (nonatomic, strong) NSMutableArray * bokmärken; @property (nonatomic, weak) IBOutlet UITableView * tableView; - (IBAction) editBookmarks: (id) avsändare; - (IBAction) addBookmark: (id) avsändare; @slutet

Börja med att dra en navigeringsfält till vår vyskontrollerns vy och placera den högst upp. Dra en förekomst av UIBarButtonItem till vänster om navigeringsfältet och ange dess identifierare i Attribut Inspector till Redigera. Styr dra från redigeringsknappen till vår Filens ägare och välj editBookmarks: metod. Dra ett andra streckknapppunkt till höger om navigeringsfältet och ge det en identifierare av Lägg till. Styr dra från add-knappen till vår Filens ägare och välj Lägg till bokmärke: metod. Slutligen dra en instans av UITableView till vår vy kontrollörens vy och ansluta sin datakälla och delegera uttag till Filens ägare objekt. Gjort.


Genomförandet av vår tabellvyns datakälla och delegera protokoll är enkel och okomplicerad. I numberOfSectionsInTableView: metod, verifierar vi om vår datakälla, det vill säga våra bokmärken, inte är noll. Om det är noll returnerar vi 1. Om inte, returnerar vi 0. Den Tableview: numberOfRowsInSection: Metoden är nästan identisk. I stället, om vår datakälla inte är noll, returnerar vi antalet element som den innehåller. Om vår datakälla är noll returnerar vi 0.

 - (NSInteger) numberOfSectionsInTableView: (UITableView *) tableView om (self.bookmarks) return 1;  annars return 0;  - (NSInteger) tableView: (UITableView *) tableView numberOfRowsInSection: (NSInteger) avsnitt if (! Self.bookmarks) return 0;  annat return self.bookmarks.count; 

I Tableview: cellForRowAtIndexPath: metod börjar vi genom att deklarera en statisk cellidentifierare för cellåteranvändning och sedan fråga tabellvyn för en återanvändbar cell med den cellidentifierare vi justerat. Om en återanvändbar cell inte returnerades, initierar vi en ny cell med en stil på UITableViewCellStyleSubtitle och vi skickar vår cellidentifierare för cellåtervinning. Därefter hämtar vi rätt bokmärke från datakällan. Varje bokmärke kommer att vara en ordbok med två nyckelvärdespar, a namn och a URL. Vi konfigurerar cellen genom att ange dess etikett och detaljetikett med respektive bokmärkes namn och webbadress.

 - (UITableViewCell *) tableView: (UITableView *) aTableView cellForRowAtIndexPath: (NSIndexPath *) indexPath static NSString * CellIdentifier = @ "Cell Identifier"; UITableViewCell * cell = [aTableView dequeueReusableCellWithIdentifier: CellIdentifier]; om (cell == nil) cell = [[UITableViewCell-allokering] initWithStyle: UITableViewCellStyleSubtitle reuseIdentifier: CellIdentifier];  // Hämta bokmärke NSDictionary * bookmark = [self.bookmarks objectAtIndex: indexPath.row]; // Konfigurera Cell cell.textLabel.text = [bookmark objectForKey: @ "name"]; cell.detailTextLabel.text = [bookmark objectForKey: @ "url"]; returcell; 

Användaren har också möjlighet att redigera sina bokmärken. I Tableview: canEditRowAtIndexPath: metod vi återvänder JA. De Tableview: commitEditingStyle: forRowAtIndexPath: är något mer komplex. Vi börjar med att verifiera att cellens redigeringsstil är lika med UITableViewCellEditingStyleDelete, det vill säga ett bokmärke har tagits bort. Först uppdaterar vi vår datakälla genom att radera bokmärket från bokmärkesmatrisen. Vi sparar sedan datakällan genom att skicka vår kontroller a saveBookmarks meddelande och vi uppdaterar slutligen tabellvyn för att återspegla de förändringar som vi gjort till datakällan.

 - (BOOL) tableView: (UITableView *) tableView canEditRowAtIndexPath: (NSIndexPath *) indexPath returnera YES;  - (void) tableView: (UITableView *) aTableView commitEditingStyle: (UITableViewCellEditingStyle) editingStyle forRowAtIndexPath: (NSIndexPath *) indexPath if (editingStyle == UITableViewCellEditingStyleDelete) // Uppdatera bokmärken [self.bookmarks removeObjectAtIndex: indexPath.row]; // Spara bokmärken [self saveBookmarks]; // Uppdatera tabellvy [aTableView deleteRowsAtIndexPaths: [NSArray arrayWithObject: indexPath] withRowAnimation: UITableViewRowAnimationFade]; 

Låt oss ta en titt på våra handlingar nu. De editBookmarks: Metoden kunde inte vara enklare. Vi byter redigeringsläget för tabellvisningen på ett animerat sätt.

 - (IBAction) editBookmarks: (id) avsändare [self.tableView setEditing:! Self.tableView.editing animerad: YES]; 

De Lägg till bokmärke: Metoden kräver lite mer arbete. Vi initierar en ny instans av AddBookmarkViewController, en vy kontroller vi kommer att skapa inom kort, och vi ställer in det är visa kontrollen egenskapen till själv. Vi presenterar sedan den nybildade bildkontrollen modellt. Som namnet antyder, AddBookmarkViewController ansvarar för att skapa nya bokmärken. Låt oss ta en närmare titt på AddBookmarkViewController.

 - (IBAction) addBookmark: (id) avsändare // Initialize Lägg till bokmärke Visa Controller AddBookmarkViewController * vc = [[AddBookmarkViewController alloc] initWithNibName: @ "AddBookmarkViewController" bunt: [NSBundle mainBundle]]; vc.viewController = själv; // Present View Controller Modally [self presentViewController: vc animerad: JA slutförd: noll]; 

Steg 4: Lägga till bokmärken

Genomförandet av AddBookmarkViewController är väldigt okomplicerat så jag kommer inte att gå in på för mycket detaljer. Utsiktskontrollen har en svag referens till vår huvudvynskontroller. Detta gör det möjligt att meddela vår huvudvisningskontroll när ett nytt bokmärke har skapats. Det har också två uttag av typen UITextField, som låter användaren ange ett namn och en URL för varje bokmärke.

 #importera  @ class ViewController; @interface AddBookmarkViewController: UIViewController __weak ViewController * _viewController; __weak UITextField * _nameField; __weak UITextField * _urlField;  @property (nonatomic, weak) ViewController * viewController; @property (nonatomic, weak) IBOutlet UITextField * nameField; @property (nonatomic, weak) IBOutlet UITextField * urlField; @slutet

XIB-filen innehåller en navigeringsfält längst upp med en annullera och a spara knapp. Vyn i sig innehåller de namn- och url-textfält som jag just nämnde. Knappen Avbryt och spara är ansluten till a annullera: och a spara: åtgärd. De annullera: åtgärden avvisar helt enkelt vår modal view controller. De spara: Åtgärden är lika enkel. Vi skapar ett nytt bokmärke (dvs en förekomst av NSDictionary) med de data som användaren har angett i textfälten och berätta vår huvudvisningskontrollör om det nya bokmärket. Det är viktigt att notera att detta inte är den bästa lösningen för att låta vår huvudvyn kontroller veta när ett nytt bokmärke har skapats av vår AddBookmarkViewController. Detta tillvägagångssätt introducerar snäv koppling, som bör undvikas så mycket som möjligt. Ett bättre tillvägagångssätt skulle vara att anta delegationsmönstret.


 - (IBAction) avbryta: (id) avsändare [self dismissViewControllerAnimated: YES completion: nil];  - (IBAction) spara: (id) avsändare NSString * namn = self.nameField.text; NSString * url = self.urlField.text; NSDictionary * bookmark = [[NSDictionary alloc] initWithObjectsAndKeys: namn, @ "namn", url, @ "url", noll]; [self.viewController saveBookmark: bokmärke]; [self dismissViewControllerAnimated: YES completion: nil]; 

Vi är nästan redo, men vi behöver fortfarande implementera det saveBookmark: metod i vår huvudvyn kontroller. Börja med att förklara den här metoden enligt vår uppfattningskontrollens huvudfiler och gå vidare till dess implementeringsfil. Implementeringen är minimal. Vi lägger till det nyskapade bokmärket i vår datakälla, vi sparar datakällan och sedan laddar vi om tabellvyn för att visa det bokmärke som vi just lagt till.

 - (void) saveBookmark: (NSDictionary *) bokmärke // Lägg till bokmärke i bokmärken [self.bookmarks addObject: bookmark]; // Spara bokmärken [self saveBookmarks]; // Uppdatera tabellvisning [self.tableView reloadData]; 

Steg 5: Laddar och spara

Vår applikation är inte särskilt användbar om användarens bokmärken inte sparas på disken. Användaren skulle förlora sina bokmärken varje gång programmet avslutas. Dålig användarupplevelse. Låt oss fixa det här.

I vår viewDidLoad: metod skickar vi vår kontroller a loadBookmarks meddelande. Låt oss ta en titt på loadBookmarks metod. Vi lagrar användarens bokmärken i databas för standardinställningar. Vi kontrollerar först om det redan finns en post i användarinställningsdatabasen med nyckeln bokmärken. Om så är fallet initierar vi våra bokmärken med innehållet i det lagrade objektet. Det här är inte fallet, vi initierar våra bokmärken med en tom, mutable array och lagrar den matrisen i användarens standarddatabas. Enkel. Höger?

 - (void) viewDidLoad [super viewDidLoad]; // Ladda bokmärken [självbelastningsbokmärken]; 
 - (void) loadBookmarks NSUserDefaults * ud = [NSUserDefaults standardUserDefaults]; om ([ut objectForKey: @ "bookmarks"]! = nil) // Ladda lokal kopia self.bookmarks = [NSMutableArray arrayWithArray: [ut objectForKey: @ "bokmärken"]];  else // Initialisera bokmärken self.bookmarks = [[NSMutableArray alloc] init]; // Spara lokal kopia [ut setObject: self.bookmarks forKey: @ "bookmarks"]; 

Att spara bokmärken är ännu enklare. Vi lagrar vårt bokmärkeobjekt i användarinställningsdatabasen med nyckeln bokmärken. Det är allt som finns där.

 - (void) saveBookmarks NSUserDefaults * ud = [NSUserDefaults standardUserDefaults]; [ut setObject: self.bookmarks forKey: @ "bokmärken"]; 

Det var ganska lite arbete. Du kan nu bygga och köra din ansökan. Du bör kunna lägga till bokmärken och radera bokmärken. Bokmärkenna sparas på disken så att du inte kommer att förlora några data när du avslutar programmet.


Steg 6: Synkronisera bokmärken

För att göra vår applikation verkligen lysande, använder vi iCloud för att hålla våra bokmärken synkroniserade över våra enheter. Det kommer att överraska dig hur lätt det här är. Som jag nämnde i den tidigare handledningen i denna serie fungerar iClouds Key Value Storage mycket NSUserDefaults, det vill säga, det lagrar nyckelvärdespar. I ICloud-terminologin heter butiken NSUbiquitousKeyValueStore. Låt oss börja med att spara våra bokmärken, inte bara lokalt, utan också till iCloud.

Gå över till vår saveBookmarks: metod och ändra vår metod för att se ut som nedan. Vi börjar med att hämta en referens till standardbutiken genom att ringa defaultStoreNSUbiquitousKeyValueStore klass. Återigen är det här mycket liknar NSUserDefaults. Om vår referens till butiken inte är noll lagras vi vårt bokmärkeobjekt i affären med samma nyckel som vi brukade lagra våra bokmärken i databasens standardinställningar. Slutligen synkroniserar vi butiken.

 - (void) saveBookmarks // Spara lokal kopia NSUserDefaults * ud = [NSUserDefaults standardUserDefaults]; [ut setObject: self.bookmarks forKey: @ "bokmärken"]; // Spara till iCloud NSUbiquitousKeyValueStore * store = [NSUbiquitousKeyValueStore defaultStore]; om (butik! = nil) [butik setObject: self.bookmarks forKey: @ "bookmarks"]; [Butik synkronisera]; 

Kallelse synkronisera I butiken instans synkroniseras minnesnycklarna och värdena med de som sparats på disken. Du kanske tror att den här metoden tvingar några nya nyckelvärdespar att skickas till iCloud, men det är inte så. Genom att spara minnesnycklarna till diskmeddelandet meddelas iCloud att det finns nya nyckelvärdespar som kan synkroniseras. Det är dock operativsystemet som slutligen bestämmer när det är lämpligt att synkronisera de nyligen tillförda nyckelvärdesparen med iCloud. Detta är viktigt att komma ihåg, och det är också anledningen till att ändringar som görs på en enhet inte kommer att synas direkt på en annan enhet.

Även om vi kallade synkroniserad metod i affären, detta är inte nödvändigt i de flesta situationer. Operativsystemet gör det för dig vid lämpliga tider. Visste du att NSUserDefaults har en synkronisera metod som fungerar nästan identiskt?

Du kanske undrar hur vår ansökan vet när en annan enhet har uppdaterat nyckelvärdesbutiken i iCloud och hur den kan dra i dessa ändringar. Det här är en mycket bra fråga och det här är det sista stycket av pusslet.

Varje gång nyckelfärdighetsbutiken har ändrats skickas en anmälan och vår ansökan kan registreras som en obeserver för dessa meddelanden. Det är viktigt att du registrerar dig för sådana anmälningar så tidigt som möjligt i din ansökans livscykel.

Låt oss se hur det här fungerar. I vår viewDidLoad metod vi gör fyra saker. Först får vi en hänvisning till Key Value Store. För det andra lägger vi till vår synkontroll som observatör för eventuella meddelanden med namnet NSUbiquitousKeyValueStoreDidChangeExternallyNotification skickad av nyckelföretaget. När vi får en sådan anmälan hanterar vi den här meddelandet i vår updateKeyValuePairs: metod (som vi skriver på ett ögonblick). Därefter skickar vi butiken ett meddelande om synkronisera. Slutligen laddar vi våra bokmärken som vi gjorde tidigare.

 - (void) viewDidLoad [super viewDidLoad]; NSUbiquitousKeyValueStore * store = [NSUbiquitousKeyValueStore defaultStore]; [[NSNotificationCenter defaultCenter] addObserver: självväljare: @selector (updateKeyValuePairs :) namn: NSUbiquitousKeyValueStoreDidChangeExternallyNotification object: store]; // Synkronisera Butik [Butik synkronisera]; // Ladda bokmärken [självbelastningsbokmärken]; 

Allt som är kvar för oss att göra är att genomföra updateKeyValuePairs: metod. Låt oss göra det just nu. Meddelandet är användarinformation ordbok innehåller två viktiga nyckelvärdespar, (1) anledning varför anmälan skickades och (2) nycklar i nyckelvärdesbutiken vars värden ändrades. Vi börjar med att titta närmare på orsaken till anmälan. Vi försäkrar först att en orsak har angivits och returneras om inget anges. Om en orsak verkligen var angiven fortsätter vi bara om anledningen var antingen en förändring på servern (NSUbiquitousKeyValueStoreServerChange) eller lokala ändringar kasseras på grund av en inledande synkronisering med servern (NSUbiquitousKeyValueStoreInitialSyncChange). Om något av dessa kriterier är uppfyllt, drar vi ut den uppsättning nycklar som ändrats och vi itererar över nycklarna för att se om vår bokmärkesnyckel är bland dem. Om så är fallet tar vi värdet förknippat med nyckeln och uppdaterar vår datakälla såväl som databasens standardinställningar med detta värde. Slutligen laddar vi upp tabellvyn för att återspegla ändringarna.

 - (void) updateKeyValuePairs: (NSNotification *) notification NSDictionary * userInfo = [notification userInfo]; NSNumber * changeReason = [userInfo objectForKey: NSUbiquitousKeyValueStoreChangeReasonKey]; NSInteger orsak = -1; // Är en orsak angiven? om (! changeReason) return;  else reason = [changeReason integerValue];  // Fortsätt om orsaken var (1) Ändringar på server eller (2) Initial synkronisering om ((anledning == NSUbiquitousKeyValueStoreServerChange) || (anledning == NSUbiquitousKeyValueStoreInitialSyncChange)) NSArray * changedKeys = [userInfo objectForKey: NSUbiquitousKeyValueStoreChangedKeysKey]; NSUbiquitousKeyValueStore * store = [NSUbiquitousKeyValueStore defaultStore]; // Söknycklar för "bokmärken" Nyckeln till (NSString * nyckeln i changedKeys) if ([key isEqualToString: @ "bokmärken"]) // Uppdatera datakälla self.bookmarks = [NSMutableArray arrayWithArray: [lagra objectForKey: key] ]; // Spara lokal kopia NSUserDefaults * ud = [NSUserDefaults standardUserDefaults]; [ut setObject: self.bookmarks forKey: @ "bokmärken"]; // Uppdatera tabellvisning [self.tableView reloadData]; 

Det finns två punkter som kräver särskild uppmärksamhet. Först, som vi såg i genomförandet av updateKeyValuePairs:, vi får en array som innehåller alla nycklar i nyckelförvaltningen med värden som har ändrats. Det här är en optimering för att förhindra att iCloud behöver skicka en anmälan för varje nyckelvärdespar som ändrats. För det andra rekommenderar vi starkt att du lagrar alla data från Key Value Store lokalt. Databasen för användarens standard är väl lämpad för detta ändamål, men du kan välja vilken lösning som passar dina behov. Anledningen till att lagra en lokal kopia är att inte förlita sig på iCloud för datalagring. Inte alla användare har ett iCloud-konto eller har iCloud aktiverat på sin enhet.

Med det här sista stycket kod på plats, är vår ansökan nu iCloud aktiverad. Bygg och kör din applikation på två enheter och testa den själv. Observera att ändringarna inte är momentana. Ändringar måste synkroniseras med iCloud-servrarna och skickas därefter till lämpliga enheter som kräver uppdatering.

Trots att denna tuturial är lång, krävde inte implementeringen av iCloud Key Value Storage att så mycket extra kod. Som jag skrev i den tidigare handledningen är det enkelt, enkelt att anta Key Value Storage, och kräver mycket lite överhuvudtaget från din sida.


Slutsats

Innan du lägger i denna handledning vill jag upprepa för och nackdelar med iCloud Key Value Storage som de är viktiga att tänka på. Fördelarna är uppenbara nu, det är lätt att anta, snabbt att genomföra, och det liknar väldigt mycket hur NSUserDefaults Arbetar. Det är dock också viktigt att hålla nackdelarna i åtanke. Nyckelvärdespar är vad de är. Det är enkla par utan någon form av konflikthantering om du inte implementerar din egen konflikthanteringslogik. Det senare rekommenderas inte eftersom Key Value Storage inte byggdes med detta i åtanke. Dokumentlagring ger inbyggt konfliktstöd och är därför ett mycket bättre alternativ om du behöver konflikthantering. Slutligen glöm inte att Key-Value Storage endast kan lagra 1MB värde av data med högst 1024 nyckelvärdespar. Trots att vi antog Key Value Storage i denna applikation för illustration, kan vi inte garantera att det aldrig kommer att finnas en användare med en lista med bokmärken som överstiger 1 MB gränsen.

Jag vill också betona att syftet med vår ansökan är att visa dig hur du ansluter nyckelfärdig lagring och hur det fungerar bakom kulisserna. Detta är inte på något sätt en applikation som är klar för utlösning eftersom den inte är kollisionsskyddad på flera sätt.


Nästa gång

I denna handledning lärde vi oss hur vi ställer in en applikation för användning med Apples iCloud. Vi tittade också på iCloud Key-Value Storage. I nästa handledning kommer vi att fokusera på den andra typen av iCloud Storage: Document Storage. Denna typ av iCloud Storage är inriktad på data tunga applikationer och det är precis vad vi ska bygga i nästa handledning.