iOS:EKEventStore sources / defaultCalendarForNewEvents / calendarsForEntityType all在授权后不返回任何内容

我有一个应用程序,我试图帮助走出门。 这段代码最初是由另一个团队用iOS5编写的。 我添加了requestAccessToEntityType:completion:成功运行的调用。 但是,在被授予访问权限后,我没有基于实体的source / defaultCalendar或日历。 我无法创建新的日历。

调用defaultCalendarForNewEvents时出现此错误

Error Domain=EKCADErrorDomain Code=1013 "The operation couldn't be completed. (EKCADErrorDomain error 1013.)" ,结果为零。

如果我退出viewController尝试执行此操作并返回,则一切正常。 如果在收到关于无源的警报后,我继续尝试(没有退出viewController),它反复失败。

我想强调的是,授权调用有效(要求用户访问日历并提供日历,以及稍后调用以确认授权通过)。 我发现的所有其他问题都与解决方案类似 – 确保您requestAccessToEntityType

 [eventStore requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) { if (granted) { //[self performSelectorOnMainThread:@selector(doScheduleActivity:) withObject:activity waitUntilDone:YES]; dispatch_async(dispatch_get_main_queue(), ^{ [self doScheduleActivity:activity]; }); } else { // probably should force the main thread dispatch_async(dispatch_get_main_queue(), ^{ UIAlertView *av = [[UIAlertView alloc] initWithTitle:@"Calendar Access Required" message:@"In order to schedule activities, APP needs access to your Calendar. You can change this in your device Settings." delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil]; [av show]; }); } }] ; 

granted回来的真实和[自己的doScheduleActivity:被调用。 以下代码是在该例程的最开始时调用的函数,其中包含失败的函数。

 EKCalendar *saCalendar; EKSource *source; NSError *error; UIAlertView *alert; LogDebug(@"eventStore defaultCalendar %@", [eventStore defaultCalendarForNewEvents]); // validate access to calendar prior to segueing if ([EKEventStore respondsToSelector:@selector(authorizationStatusForEntityType:)]) { switch([EKEventStore authorizationStatusForEntityType:EKEntityTypeEvent]) { case EKAuthorizationStatusAuthorized: break; case EKAuthorizationStatusNotDetermined: { dispatch_async(dispatch_get_main_queue(), ^{ UIAlertView *alert = [[UIAlertView alloc] initWithTitle:SA_ALERT_CAPTION_CALENDAR_ACCESS_NOT_DETERMINED message:SA_ALERT_BODY_CALENDAR_ACCESS_NOT_DETERMINED delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil]; [alert show]; }); return false; } case EKAuthorizationStatusDenied: { dispatch_async(dispatch_get_main_queue(), ^{ UIAlertView *alert = [[UIAlertView alloc] initWithTitle:SA_ALERT_CAPTION_CALENDAR_ACCESS_DENIED message:SA_ALERT_BODY_CALENDAR_ACCESS_DENIED delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil]; [alert show]; }); return false; } case EKAuthorizationStatusRestricted: { dispatch_async(dispatch_get_main_queue(), ^{ UIAlertView *alert = [[UIAlertView alloc] initWithTitle:SA_ALERT_CAPTION_CALENDAR_ACCESS_RESTRICTED message:SA_ALERT_BODY_CALENDAR_ACCESS_RESTRICTED delegate:nil cancelButtonTitle:@"Ok" otherButtonTitles:nil]; [alert show]; }); return false; } default: break; } } // search for application specifc calendar.. saCalendar = nil; for(EKCalendar *calendar in [eventStore calendarsForEntityType:EKEntityTypeEvent]) { if([calendar.title isEqualToString:SA_ACTIVITIES_CALENDAR_TITLE]) { saCalendar = calendar; break; } } // ..and create from scratch if nonexistent if(nil == saCalendar) { // find local source to hook up new calendar to for(source in [eventStore sources]) { if(source.sourceType == EKSourceTypeLocal) { break; } } // if could not find local source type, something is wrong if( source == nil || source.sourceType != EKSourceTypeLocal) { alert = [[UIAlertView alloc] initWithTitle:SA_ALERT_CAPTION_CALENDAR_ERROR_NO_SOURCE message:SA_ALERT_BODY_CALENDAR_ERROR delegate:self cancelButtonTitle:@"Ok" otherButtonTitles:nil]; [alert show]; return false; } // create calendar for applcation, name it, color it and assign source saCalendar = [EKCalendar calendarForEntityType:EKEntityTypeEvent eventStore:eventStore]; [saCalendar setSource:source]; [saCalendar setTitle:SA_ACTIVITIES_CALENDAR_TITLE]; [saCalendar setCGColor:[[UIColor yellowColor] CGColor]]; // create immediately error = nil; if(![eventStore saveCalendar:saCalendar commit:true error:&error]) { dispatch_async(dispatch_get_main_queue(), ^{ UIAlertView *alert = [[UIAlertView alloc] initWithTitle:SA_ALERT_CAPTION_CALENDAR_ERROR_CANT_SAVE message:SA_ALERT_BODY_CALENDAR_ERROR delegate:self cancelButtonTitle:@"Ok" otherButtonTitles:nil]; [alert show]; }); return false; } } return true; 

一切都回来了,虽然它被授权并且检查[EKEventStore authorizationStatusForEntity:EKEntityType返回EKAuthorizationStatusAuthorized

我在这里遇到失败后,如果我退出这个视图控制器并返回,它就可以了。 这仅在系统第一次要求用户进行日历访问时才会发生,并且他们回复OK。

感谢您的任何见解。 我一直在单步执行调试器,并且还进行printf类型调试以避免任何类型的计时问题等,并且没有看到与我在Apple站点上查找的事件相反的事情。

我的目标设备是6.1.3 iPhone 5

好的,事实certificate在viewDidLoad中有一小段代码在[eventStore requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error代码并试图访问eventStore。这是多余的,不需要发生了,我没有注意到。一旦我删除了这些代码,现在的东西就可以了,所以它确实需要授权,因为即使在授权之后,由于之前的访问,eventStore已经“糟糕”了。

一旦授予访问权限,通过在回调中重新创建EKEventStore实例也可以解决该问题。