iOS Timer se ejecuta en segundo plano

Mi aplicación requiere llamar a un método periódicamente.

Esta llamada debe hacerse incluso si la aplicación se puso en segundo plano.

La hora en que la aplicación puede estar en segundo plano no está definida, siempre que la aplicación puede pasar de estar en segundo plano para reanudarse.

Tengo una class para administrar el timer:

@protocol TimerDelegate <NSObject> - (void)startTimerAction:(id)userInfo; @end @interface TimerController : NSObject{ NSTimer *repeatingTimer; id <TimerDelegate> delegate; } + (TimerController *)shanetworkingInstance; - (void)startTimerForSender:(id <TimerDelegate>)sender withTimeInterval:(NSTimeInterval)time; - (void)stopTimer; @end 

Implementación:

 #import "TimerController.h" TimerController *singletonInstance; @implementation TimerController #pragma mark - Singleton + (TimerController *)shanetworkingInstance { if (singletonInstance == nil) { singletonInstance = [[super allocWithZone:NULL] init]; } return singletonInstance; } + (id)allocWithZone:(NSZone *)zone { return [self shanetworkingInstance]; } - (id)copyWithZone:(NSZone *)zone { return self; } #pragma mark - Public - (void)startTimerForSender:(id <TimerDelegate>)sender withTimeInterval:(NSTimeInterval)time { if (repeatingTimer) { [self stopTimer]; } if (sender) { delegate = sender; } if (time > 0.0) { NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:time target:self selector:@selector(targetMethod:) userInfo:[self userInfo] repeats:YES]; repeatingTimer = timer; } } - (void)stopTimer { if (repeatingTimer) { [repeatingTimer invalidate]; repeatingTimer = nil; } } - (NSDictionary *)userInfo { return @{@"StartDate" : [NSDate date]}; } - (void)targetMethod:(NSTimer*)theTimer { if (delegate && [delegate respondsToSelector:@selector(startTimerAction:)]) { [delegate startTimerAction:[repeatingTimer userInfo]]; } } @end 

Utilizo la class TimerController de esta manera:

 -(void)viewDidLoad{ [super viewDidLoad] TimerController *timerC = [TimerController shanetworkingInstance]; [timerC startTimerForSender:self withTimeInterval:30]; } #pragma mark - TimerDelegate - (void)startTimerAction:(id)userInfo { NSLog(@"Method called"); } 

Puedo leer en inputs NSLog cada 30 segundos. Poner la aplicación en segundo plano hace que el timer se detenga y no escriba loggings cada 30 segundos, cuando la aplicación reanude el timer funciona correctamente.

Necesito llamar al método cada 30 segundos, aunque la aplicación está en segundo plano.

Leí esta pregunta: timer en modo de background

Debo poder enviar una request a AppStore.

Gracias

 - (void)applicationDidEnterBackground:(UIApplication *)application { bgTask = [application beginBackgroundTaskWithExpirationHandler:^{ // Clean up any unfinished task business by marking where you // stopped or ending the task outright. [application endBackgroundTask:bgTask]; bgTask = UIBackgroundTaskInvalid; }]; // Start the long-running task and return immediately. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ // Do the work associated with the task, preferably in chunks. [application endBackgroundTask:bgTask]; bgTask = UIBackgroundTaskInvalid; }); } 

fuente: iPhone Programmig Guide

pregunta similar: https://stackoverflow.com/a/8613624/1827690

Para ejecutar su aplicación en segundo plano de forma continua, debe registrar su aplicación para los modos de background requeridos en plist

Documentación