Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Throttle the Frequency of Location Updates to Firebase #9

Open
fne00 opened this issue Jan 23, 2020 · 21 comments
Open

Throttle the Frequency of Location Updates to Firebase #9

fne00 opened this issue Jan 23, 2020 · 21 comments
Labels
enhancement New feature or request

Comments

@fne00
Copy link

fne00 commented Jan 23, 2020

Chris,
My app needs frequent location updates to perform its functions, but I only need less frequent location updates to Firebase.

Would you consider adding a parameter such as:

  • firebase_update_interval (seconds)
    such that a location update would not be sent to firebase if a previous location had been sent within firebase_update_interval seconds.

I would continue to take location updates as quickly as they are available, but set this to parameter somewhere in the range 10 to 60 seconds.

Alternatively is there a way I can intercept updates to firebase myself to achieve this?

Peter

@christocracy
Copy link
Member

There is no way to handle this currently. It would not be implemented in the Firebase adapter, it would should be implemented in flutter_background_geolocation.

@christocracy
Copy link
Member

You could manually manage this via BackgroundGeolocation#setConfig with Config.maxRecordsToPersist, oscillating between setting that to 0 and -1 with your own logic.

@fne00
Copy link
Author

fne00 commented Jan 24, 2020

Chris,
Thanks for the suggestion, but it's not working for me (as yet, anyway).

In my void _onLocation(bg.Location location)
I have added:

   // handle throttling updates to Firebase
    if (liveFireStoreEnabled)  {

      DateTime now = DateTime.now();
      if(now.isAfter(lastUpdateToFirebase.add(Duration(seconds: liveFireStoreInterval ))))
      {
        bg.BackgroundGeolocation.setConfig(bg.Config(maxRecordsToPersist: -1)); // no limit - store point(s) to SQL and Firebase
        lastUpdateToFirebase = now;
        print('&&&&&&&&&Firestore Insert ON &&&&&&&&&&');

      } else {
        bg.BackgroundGeolocation.setConfig(bg.Config(maxRecordsToPersist: 0)); // don't store this point
        print('&&&&&&&&&Firestore Insert OFF &&&&&&&&&&');
      }
    }

But see the attached log, which seems to show:

  • With liveFireStoreInterval set to 10
  • As locations come in, the test seems to be working to flip between the two .setConfig's (off for 10 secs and then back on for one location).
  • But I am still getting a Firestore INSERT: for each location.

Testing on a real Android device indicates I am still getting all locations sent to Firebase.

Your insights would be appreciated.

MapRunF Log - Firebase v1.txt

@christocracy
Copy link
Member

Set it 0 and keep it 0. You’ll find nothing gets persisted.

@fne00
Copy link
Author

fne00 commented Jan 24, 2020

But if I do that, won't I get no locations sent to Firebase? I still want a location sent every 10 seconds.

@christocracy
Copy link
Member

I’m asking you to do a test, to perform an extreme case and determine the outcome.

@fne00
Copy link
Author

fne00 commented Jan 24, 2020

OK - Sorry - my misunderstanding.

I have set both branches of the if statement to:
bg.BackgroundGeolocation.setConfig(bg.Config(maxRecordsToPersist: 0))

All locations are still being sent to Firebase...!

@christocracy
Copy link
Member

You needn’t provide exclamations (!). Just provide the facts and I’ll look into it.

@fne00
Copy link
Author

fne00 commented Jan 24, 2020

OK not meaning to imply anything.

Just is case it's relevant, in my initial bg.config I have:

      bgConfigToApply = bg.Config(
          persistMode: saveToBGsqlDBandLiveTrack,
         .....

where

    int saveToBGsqlDBandLiveTrack = liveFireStoreEnabled
        ? bg.Config.PERSIST_MODE_ALL
        : bg.Config.PERSIST_MODE_NONE;

@fne00
Copy link
Author

fne00 commented Feb 3, 2020

Chris,

I've changed my manual throttling of location updates to Cloud Firestore, to the following.

    // handle throttling updates to Firebase
    if (liveFireStoreEnabled)  {
      DateTime now = DateTime.now();
      if(now.isAfter(lastUpdateToFirebase.add(Duration(seconds: liveFireStoreInterval ))))
      {
        bg.BackgroundGeolocation.setConfig(bg.Config(persistMode: bg.Config.PERSIST_MODE_ALL)); // store point(s) to SQL and Firebase
        lastUpdateToFirebase = now;
        print('&&&&&&&&&Firestore Insert ON &&&&&&&&&&');
      } else {
        bg.BackgroundGeolocation.setConfig(bg.Config(persistMode: bg.Config.PERSIST_MODE_NONE)); // don't store to SQL/Firebase
        print('&&&&&&&&&Firestore Insert OFF &&&&&&&&&&');
      }
    }

Testing so far indicates that this is working. That is:

  • onLocation is still giving me all locations (say 1 per second) for local processing in my App, and
  • Firebase is getting locations at say 1 per 30 seconds.

My questions is:

  • Can you see any problems with this approach? (eg I don't know how onerous the process is of changing the persistMode in the bg package).

Thanks

@fne00
Copy link
Author

fne00 commented Feb 26, 2020

Chris,
I appreciate that my question above is not top of your priority list, so I've deployed this solution to my production App anyway.
It seems to work OK.
One implication I can see from this approach is, that when the user drops off line, I am effectively discarding the data. So the solution is not ideal.
Would you consider my original post on this issue to be an enhancement request please. (or other suggestions are welcome).
Thanks

@christocracy christocracy added the enhancement New feature or request label Feb 26, 2020
@christocracy
Copy link
Member

Yes, but I won’t be able to get around to starting on this this for at least a month.

@fne00
Copy link
Author

fne00 commented Feb 26, 2020

OK - thanks - no problems - I'll look forward to it in due course.

@fne00
Copy link
Author

fne00 commented Jun 24, 2020

Chris,
Is this still in your forward plans? I certainly would find it valuable for my MapRunF App, and I can't think of a way to achieve the outcome without a change in this Package.
Thanks

@fne00
Copy link
Author

fne00 commented Oct 26, 2020

Chris,
Is this in your current plans? Anything I can do to assist? (I'm assuming it would require changes on the native end(s) - which is why I haven't tried to adapt your Dart code).

Context: My MapRunF App is being used by runners for 8,000-10,000 runs per month. Some organising clubs would like live tracking...but if I push all data to Firebase, I get too much data. With my current approach to culling the data (as above), I lose data if there is no data connection. I guess I could revert to sending all data from the App to Firebase and then culling it there with a Firebase Function ... but I could incur higher usage charges from Google.
Thanks Peter

@christocracy
Copy link
Member

What's wrong with the solution you posted above using persistMode?

@fne00
Copy link
Author

fne00 commented Oct 26, 2020

Chris,

I'm pretty sure that when I do:
bg.BackgroundGeolocation.setConfig(bg.Config(persistMode: bg.Config.PERSIST_MODE_NONE));

any data queued up in the internal SQL database (that hasn't been sent to Firebase) will be discarded. This is OK if the device is always online (as I assume lost data would be minimal), but for the types of events we run, that can't be assumed.

Peter

@christocracy
Copy link
Member

any data queued up in the internal SQL database (that hasn't been sent to Firebase) will be discarded

When you activate the Firebase Adapter, persistence to background-geolocation's SQLite database is disabled. Firebase automatically handles on-device queuing of data when there's no network connection.

@fne00
Copy link
Author

fne00 commented Oct 28, 2020

Thanks - Looks like I have made incorrect assumptions, and so my current approach of throttling updates to Firebase may well be adequate. I'll do some more thorough testing.

@mrruby
Copy link

mrruby commented Feb 24, 2021

@christocracy Any update on this? I am looking for the same behavior of sending location into the database with an interval of not less than 20 minutes.

Setting persistMode approach is ok?

@christocracy
Copy link
Member

Config.persistMode is a flag. Whenever a location or geofence event occurs, BackgroundGeolocation evaluates that flag when deciding whether to broadcast that location/geofence event on to the Firebase adapter.

You are free to switch that persistMode flag at any time and however often your wish.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

3 participants