2012-08-16 5 views
5

Per la mia app, utilizzo la memorizzazione dei valori delle chiavi di iCloud per memorizzare alcune impostazioni dell'utente. Si sincronizza perfettamente tra il mio iPad e iPhone quando entrambi hanno installato l'app. Il mio problema è che quando elimino l'app e la eseguo correttamente, non ho nessuna delle impostazioni di iCloud la PRIMA VOLTA che lo eseguo. Dopo averlo eseguito di nuovo, anche se non aveva le impostazioni la prima volta, ce l'ha.iCloud non funziona L'app per la prima volta viene avviata

Ho usato alcuni NSlog per vedere cosa vede nel contenitore dei valori-chiave, e la prima volta che l'app funziona fresco dice "(null)", ma ogni successiva esecuzione stampa l'NSArray che è stato precedentemente salvato.

Fornirò volentieri il codice, ma non sono del tutto sicuro di ciò che è rilevante qui.

Apprezzerei tutto l'aiuto, questo problema mi sta facendo impazzire ...

risposta

6

Aggiungi un osservatore per NSUbiquitousKeyValueStoreDidChangeExternallyNotification e la sincronizzazione NSUbiquitousKeyValueStore. Attendi che venga richiamata presto la funzione di callback.

if([[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil]) 
{ 
    [[NSNotificationCenter defaultCenter] addObserver:self 
              selector:@selector(keyValueStoreChanged:) 
               name:NSUbiquitousKeyValueStoreDidChangeExternallyNotification 
               object:[NSUbiquitousKeyValueStore defaultStore]]; 

    [[NSUbiquitousKeyValueStore defaultStore] synchronize]; 
} 
else 
{ 
     NSLog(@"iCloud is not enabled"); 
} 

e quindi utilizzare NSUbiquitousKeyValueStoreChangeReasonKey di distinguere tra una prima sincronizzazione tempo e il cambiamento del server di sincronizzazione.

-(void)keyValueStoreChanged:(NSNotification*)notification 
{ 
    NSLog(@"keyValueStoreChanged"); 

    NSNumber *reason = [[notification userInfo] objectForKey:NSUbiquitousKeyValueStoreChangeReasonKey]; 

    if (reason) 
    { 
     NSInteger reasonValue = [reason integerValue]; 
     NSLog(@"keyValueStoreChanged with reason %d", reasonValue); 

     if (reasonValue == NSUbiquitousKeyValueStoreInitialSyncChange) 
     { 
      NSLog(@"Initial sync"); 
     } 
     else if (reasonValue == NSUbiquitousKeyValueStoreServerChange) 
     { 
      NSLog(@"Server change sync"); 
     } 
     else 
     { 
      NSLog(@"Another reason"); 
     } 
    } 
} 
+0

Curioso ... Qual è la ragione usare -URLForUbiquityContainerIdentifier: metodo su NSFileManager? –

+0

per verificare se iCloud è abilitato sul dispositivo. – erkanyildiz

+1

Nota: avere sempre un fallback per tutti gli altri motivi. Questo è molto importante. Puoi considerare tutti gli altri motivi non gestiti allo stesso modo in cui esegui le normali modifiche al server. – Julien

1

Ci potrebbe essere un ritardo tra la vostra applicazione in fase di installazione (e lanciato) e KVS scaricando i valori iniziali. Se si registra correttamente alla notifica di modifica, si dovrebbe vedere i valori in arrivo

Il codice dovrebbe essere sempre l'aspetto di questo, in generale il metodo di -applicationDidFinishLaunching: delegato:.

_store = [[NSUbiquitousKeyValueStore defaultStore] retain]; // this is the store we will be using 
// watch for any change of the store 
[[NSNotificationCenter defaultCenter] addObserver:self 
     selector:@selector(updateKVStoreItems:) 
     name:NSUbiquitousKeyValueStoreDidChangeExternallyNotification 
     object:_store]; 
// make sure to deliver any change that might have happened while the app was not launched now 
[_store synchronize];