AbdFatah / analytics-issues

Automatically exported from code.google.com/p/analytics-issues
0 stars 0 forks source link

manual dispatch doesn't work when iOS app is going to background #250

Open GoogleCodeExporter opened 9 years ago

GoogleCodeExporter commented 9 years ago
Name of affected component: ??, guessing it's Core Reporting API

Product: iOS SDK v2beta3

Issue summary:
I've been working with Google's Analytics SDK v2beta3 and have everything 
working except I can't get manual dispatch to work when the app leaves the 
active state. (fyi, for my app I need to reserve battery power so am only using 
'[[GAI sharedinstance] dispatch]' to dispatch my event data when the user is 
finished with the app.)  

I've tried several things, but while the dispatch call is reached and run 
during tracing, it doesn't seem to do anything... no log output (I have debug 
mode on) and no data uploaded. It should minimally report "GoogleAnalytics 
2.0b3 -[GAIDispatcher initiateDispatch:retryNumber:] (GAIDispatcher.m:479) 
DEBUG: No pending hits." or something of that sort I would think. But nothing 
in the log and no data sent. It's as if GAI has shut down.

Instead, when the app resumes from background, the hits are then transmitted 
and I see all the debug statements on my console and data is sent successfully 
to my Google Analytics account.  

Below is my code...

    - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
    {
        ...
        // set up Google Analytics tracker
        [GAI sharedInstance].trackUncaughtExceptions = YES; // automatically track uncaught exceptions with Google Analytics - sent with stack trace.
        [GAI sharedInstance].dispatchInterval = -1;         // set Google Analytics dispatch off, will do manually when app goes into background.
        [GAI sharedInstance].debug = YES;                   // set debug to YES for extra debugging information.
        id<GAITracker> tracker = [[GAI sharedInstance] trackerWithTrackingId:GOOGLE_ANALYTICS_TRACKING_ID_FOR_TEST];    // Create tracker instance.
        [tracker setSessionTimeout:600];                     // set min time between sessions to be 10 minutes
        [GAI sharedInstance].defaultTracker = tracker;   // reset the default tracker if needed
        [[GAI sharedInstance] setOptOut:NO];

        ...
    }

     - (void)applicationWillResignActive:(UIApplication *)application
    {
        UIDevice * device = [UIDevice currentDevice];
        BOOL backgroundTasksSupported = NO;

        if ([device respondsToSelector:@selector(isMultitaskingSupported)]) {
            backgroundTasksSupported = device.multitaskingSupported;
        }

        if (backgroundTasksSupported) {
            self.uploadAnalyticsBackgroundTask = [application beginBackgroundTaskWithExpirationHandler:^{[self endBackgroundUploadTask];}];

            // Start the long-running task and return immediately.
            dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{        // put block on Global run queue...

                [[GAI sharedInstance] dispatch];                                                    // for dispatch of collected metric/analysis data...

                [self endBackgroundUploadTask];
            });
        }
        else {
            [[GAI sharedInstance] dispatch];
        }

    }

    - (void) endBackgroundUploadTask
    {
         if(self.uploadAnalyticsBackgroundTask != UIBackgroundTaskInvalid) {          // if background task running, end it
            [[UIApplication sharedApplication] endBackgroundTask: self.uploadAnalyticsBackgroundTask];
            self.uploadAnalyticsBackgroundTask = UIBackgroundTaskInvalid;
         }
    }

The app reaches and executes the '[[GAI sharedInstance] dispatch];' line, but 
does nothing.
I'm quite a newbie with background tasks when the app goes to the background so 
maybe I'm doing something wrong. But as part of my investigations I've even 
simplified applicationWillResignActive to this (which is/should be blocking)... 
 but I get the same thing: no debug info and no transmitted data.

     - (void)applicationWillResignActive:(UIApplication *)application
    {
        [[GAI sharedInstance] dispatch];
    }

If tried it with the dispatch interval non-negative (say 15 seconds) and I get 
regular transmission at the requested interval, but the call to manually 
dispatch doesn't work.

Calls to manual dispatch in other parts of my code do work.  It just seems that 
it doesn't work when the app is closing down. 

Any thoughts advice on what I might have done wrong and how I can fix this? 

Expected output:
manual dispatch during "go to background" would output debug info to console 
and transmit data like interval based dispatches

Actual results:
no debug on console and no transmitted data.   It transmits at start of next 
run, when app is brought up again.

Original issue reported on code.google.com by sma...@leftcoastbiometrics.com on 14 Dec 2012 at 11:12

GoogleCodeExporter commented 9 years ago
[deleted comment]
GoogleCodeExporter commented 9 years ago
I have the same problem. I click a button and it opens the AppStore 
application. I call the [[GAI sharedInstance] dispatch]; after the sendEvent in 
applicationWillResignActive, applicationDidBecomeActive, 
applicationWillTerminate. 
Also tried:
1) - (void)applicationDidEnterBackground:(UIApplication *)application
{

    UIApplication *app = [UIApplication sharedApplication];

    bgTask = [app beginBackgroundTaskWithExpirationHandler:^{
        [app endBackgroundTask:bgTask];
        bgTask = UIBackgroundTaskInvalid;
    }];

    dispatch_sync(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{

        [[GAI sharedInstance] dispatch];

        [app endBackgroundTask:bgTask];
        bgTask = UIBackgroundTaskInvalid;
    });
}  
// Make the device to stay longer when the app is in background (but the 
analytics didn't came)

2) After dispatching sent a delayed action to go to the AppStore
The current logic is
TrackEvent >> Dispatch >> Go to AppStore
Below is the code I use
id <GAITracker> tracker = [[GAI sharedInstance] defaultTracker];

    [tracker sendEventWithCategory:@"..."
                            withAction:@"..."
                             withLabel:@"..."
                             withValue:nil];

    [[GAI sharedInstance] dispatch];

     [self performSelector:@selector(openAppStore) withObject:nil afterDelay:1];

Google should provide delegate methods and when the delegate has been notified 
in a protocol method then perform the action to open another app.

Thank you,
Hoping this will resolve the new SDK

Original comment by christia...@gmail.com on 20 Mar 2013 at 9:08

GoogleCodeExporter commented 9 years ago

Original comment by pfrise...@google.com on 10 Oct 2014 at 6:13