{"id":16352387,"url":"https://github.com/maxim-saplin/ambilytics","last_synced_at":"2025-03-23T01:30:54.430Z","repository":{"id":184198550,"uuid":"661989785","full_name":"maxim-saplin/ambilytics","owner":"maxim-saplin","description":"Google Analytics for all Flutter platfroms (Android, iOS, macOS, Web, Windows and Linux)","archived":false,"fork":false,"pushed_at":"2025-01-02T20:57:15.000Z","size":416,"stargazers_count":11,"open_issues_count":0,"forks_count":5,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-03-18T16:13:36.777Z","etag":null,"topics":["dart","flutter","flutter-package","ga4","google-analytics","google-analytics-4","hacktoberfest","measurement-protocol","package","product-analytics","pubdev"],"latest_commit_sha":null,"homepage":"https://pub.dev/packages/ambilytics","language":"Dart","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/maxim-saplin.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-07-04T06:01:48.000Z","updated_at":"2025-03-12T04:41:38.000Z","dependencies_parsed_at":null,"dependency_job_id":"adcdcf54-d2ae-4067-b3a0-122107c0c31d","html_url":"https://github.com/maxim-saplin/ambilytics","commit_stats":null,"previous_names":["maxim-saplin/ambilytics"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/maxim-saplin%2Fambilytics","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/maxim-saplin%2Fambilytics/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/maxim-saplin%2Fambilytics/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/maxim-saplin%2Fambilytics/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/maxim-saplin","download_url":"https://codeload.github.com/maxim-saplin/ambilytics/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":245043848,"owners_count":20551841,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["dart","flutter","flutter-package","ga4","google-analytics","google-analytics-4","hacktoberfest","measurement-protocol","package","product-analytics","pubdev"],"created_at":"2024-10-11T01:26:02.964Z","updated_at":"2025-03-23T01:30:54.422Z","avatar_url":"https://github.com/maxim-saplin.png","language":"Dart","funding_links":[],"categories":[],"sub_categories":[],"readme":"Enable Google Analytics for **all** Flutter platforms: Android, iOS, macOS, Web, Windows, and Linux.\n\nThe official Flutter plugin for Firebase Analytics (which uses Google Analytics behind the scenes) works with 4 platforms (Android, iOS, macOS, and Web). For Windows and Linux, there's no out-of-the-box support.\n\n*Ambilytics* Flutter plugin solves this issue by enabling Google Analytics 4 (GA4) Measurement Protocol for unsupported platforms (Windows and Linux) and creating a unified interface that abstracts away interaction with 2 different analytics backends:\n- Google/Firebase Analytics\n    - You enable and configure it for any of the required platforms (Android, iOS, macOS, Web)\n    - *Note:* as of July 2023 macOS is in Beta and may be displayed as iOS platform in Firebase/Google Analytics consoles, choose proper Data Stream name for it in GA console\n- GA4 Measurement Protocol\n    - You create a separate Web stream to track events sent from Windows/Linux\n\nBy creating Firebase project, configuring Google Analytics account, importing the package (and optionally setting navigation observer) you get the capability to send standard and custom events to Google Analytics and see data in Reports. \n\nProduct analytics made easy (and ambient).\n\n\u003cimg width=\"400\" alt=\"image\" src=\"https://github.com/maxim-saplin/ambilytics/blob/main/_misc/GA.png?raw=true\"\u003e\n\n# Features\n\n- Unified analytics interface for all Flutter platforms\n- Seamless interaction with Firebase Analytics and GA4 Measurement Protocol\n- Automatic app start and screen view event tracking\n    - `app_start` custom event is sent during initialization, `platform` parameter contains name of the platform\n    - When `AmbilyticsObserver` is configured `screen_view` is sent on Firebase platforms along with `screen_view_cust` via Measurement Protocol (either for all platforms or only Windows/Linux, configurable)\n- Custom event tracking\n- Configurable navigation observer for easy integration\n  - It can register `showDialog()` actions as navigation events\n- Disable analytics in one place, e.g. according to user changing preferences (a checkbox to share analytics)\n\nCheck `/example` folder for usage detail.\n\n# Challenges\n\nMeasurement Protocol can't be a complete replacement for the default Google Analytics backend:\n- Limited standard reports in GA4 for unsupported platforms\n    - You might need to create custom dimensions and customize standard reports\n- Measurement protocol doesn't support sending standard events, e.g. instead if `screen_view` events sent via Firebase, a custom event `screen_view_cust` is sent (with screen name param). \n    - This make standard Events report not useful for all 6 platforms. Yet the package allowed sending both events, which make it possible to create a custom report that can track screen views across all platforms.\n- No automatic geo, demographic, and language data collection for Measurement Protocol\n\nHence the philosophy of this package: complete analytics for the platforms supported by Firebase and essential events from unsupported platforms (Windows and Linux).\n\n# Configuring Ambilytics\n\nHistorically Firebase Analytics was used for app analytics on iOS/Android and Google Analytics for web. Now they are integrated. In order to proceed you'll need a Google Account. Using this account you will set-up a project in Firebase Console which will be linked to an account/property in Google Analytics. All reports will be available in Google Analytics Console.\n\nThe workflow has 2 steps:\n1. Configuring Firebase Analytics for complete reporting on any of the 4 platforms (Android, iOS, macOS, Web)\n2. Configuring Measurement Protocol for essential analytics on Windows and Linux\n\n\n# Configuring Firebase\n\nBellow you can find instructions for 2 scenarios:\n1. Adding analytics from scratch\n2. Adding it to existing Flutter app using Firebase Analytics\n\n\n## a) Setup from scratch\n\nThe below instructions are based on this manual: https://firebase.google.com/docs/flutter/setup?platform=ios\n\n### Prepare command-line tools\n1. Install the Firebase CLI (https://firebase.google.com/docs/cli#setup_update_cli)\n2. Log into Firebase using your Google account by running the following command:\n```bash\nfirebase login\n```\n- you can logout via `logout` command and than repeat the `login` command to change the account\n3. Install the FlutterFire CLI by running the following command from any directory:\n```bash\ndart pub global activate flutterfire_cli\n```\n- you might need to add the cli to path, e.g. `export PATH=\"$PATH\":\"$HOME/.pub-cache/bin\"` for macOS\n\n### Configure Firebase/Google Analytics for each target platform\n1. In terminal change directory to your Flutter project\n2. Run Firebase core initialization script\n```bash\nflutterfire configure\n```\n3. **Fix macOS** networking. Edit `macos\\Runner\\DebugProfile.entitlements` and `macos\\Runner\\Release.entitlements` and add `com.apple.security.network.client`, e.g.:\n```\n\t...\n  \u003ckey\u003ecom.apple.security.network.client\u003c/key\u003e\n\t\u003ctrue/\u003e\n\u003c/dict\u003e\n\u003c/plist\u003e\n```\n4. Modify and use the generated `firebase_options.dart` to initialize `Ambilytics` ([see here](#using-ambilytics-in-your-app))\n  - You need to remove unnecessary platforms from the generated file to avoid error:\n  ```dart\n    static FirebaseOptions get currentPlatform {\n    if (kIsWeb) {\n      return web;\n    }\n    switch (defaultTargetPlatform) {\n      case TargetPlatform.android:\n        return android;\n      case TargetPlatform.iOS:\n        return ios;\n      case TargetPlatform.macOS:\n        return macos;\n      default:\n        return macos;\n    }\n  }\n  ```\n5. Open Firebase Console (https://console.firebase.google.com/) and choose used above project. Click `Analytics-\u003eDashboard` tab to the left, click `Enable Google Analytics` button. You will be presented with a wizard that will link Google Analytics account to Firebase project. At the last step `Add the Google Analytics SDK` just click `Finish` button as `flutterfire configure` command above has already taken care of that.\n\nAt this point you have Firebase/Google Analytics setup for up-to 4 platforms (Android, iOS, macOS and web). Next you need to [Configure Measurement Protocol](#measurement-protocol) to cover Windows and Linux and [Start using Ambilytics in your app](#using-ambilytics-in-your-app) and start sending events.\n\n**Notes:**\n- Running the command will show the list of existing Firebase projects to choose one OR will suggest to create a new project.\n- Firebase Analytics requires native projects to be configured. I.e. various plists for macOS/iOS, google-services.json for Android etc. The above command takes care of that\n- You can have each platform configured individually/manually without any CLI (e.g. follow the instructions from Firebase console/Google Analytics console on configuring each native part individually) - though CLI seems easier and less error-prone\n- Each time a new platform is added to Flutter app you need to rerun the above command\n- App ID, API keys etc. will be saved to a newly created `firebase_options.dart` file\n- This step only covers Android, iOS, macOS and Web platforms\n- You can  skip Firebase set-up and have all 6 platforms using Measurement Protocol (assuming the challenges mentioned above)\n\n\u003cdetails\u003e\n  \u003csummary\u003e\nHere's an example for `flutterfire configure` output:\n  \u003c/summary\u003e\n\n```bash\nuser@users-MacBook-Pro example % flutterfire configure\ni Found 4 Firebase projects.                                                                                                                             \n✔ Select a Firebase project to configure your Flutter application with · \u003ccreate a new project\u003e                                                          \n✔ Enter a project id for your new Firebase project (e.g. my-cool-project) · ambilytics-example                                                           \ni New Firebase project ambilytics-example created successfully.                                                                                          \n✔ Which platforms should your configuration support (use arrow keys \u0026 space to select)? · ios, macos, web, android                                       \ni Firebase android app com.example.example is not registered on Firebase project ambilytics-example.                                                     \ni Registered a new Firebase android app on Firebase project ambilytics-example.                                                                          \ni Firebase ios app com.example.example is not registered on Firebase project ambilytics-example.                                                         \ni Registered a new Firebase ios app on Firebase project ambilytics-example.                                                                              \ni Firebase macos app com.example.example.RunnerTests is not registered on Firebase project ambilytics-example.                                           \ni Registered a new Firebase macos app on Firebase project ambilytics-example.                                                                            \ni Firebase web app ambilytics_example (web) is not registered on Firebase project ambilytics-example.                                                    \ni Registered a new Firebase web app on Firebase project ambilytics-example.                                                                              \n? The files android/build.gradle \u0026 android/app/build.gradle will be updated to apply Firebase configuration and gradle build plugins. Do you want to cont\n✔ The files android/build.gradle \u0026 android/app/build.gradle will be updated to apply Firebase configuration and gradle build plugins. Do you want to continue? · yes \n\nFirebase configuration file lib/firebase_options.dart generated successfully with the following Firebase apps:\n\nPlatform  Firebase App Id\nweb       1:777853418226:web:69da4a4f2a495cbc99cdeb\nandroid   1:777853418226:android:d5ffad29eb40783199cdeb\nios       1:777853418226:ios:5e6533e94fef227899cdeb\nmacos     1:777853418226:ios:e32e65cdbc373d6599cdeb\n\nLearn more about using this file and next steps from the documentation:\n \u003e https://firebase.google.com/docs/flutter/setup\n```\n\u003c/details\u003e\n\n## b) Adding to Flutter app already using Firebase Analytics\n\nGiven you have been using Firebase Analytics plugin, native platforms are already set (the above a) step is not necessary), you are using `FirebaseAnalytics.logEvent()` to send events and `FirebaseAnalyticsObserver` to plug-in to navigation events. In this case in order to switch to `Ambilytics` you have to:\n1. [Enable Measurement Protocol](#measurement-protocol) as described below\n2. Replace all occurrences of `FirebaseAnalytics.logEvent()` with `sendEvent()` from this package and replace `FirebaseAnalyticsObserver` with `AmbilyticsObserver`. [See using Ambilytics in your app](#using-ambilytics-in-your-app) \n\n# Measurement Protocol\n\nTo enable essential data sent from `Windows` and `Linux` you will have to create a new Web stream in Google Analytics to accept events sent via Measurement Protocol.\n\n1. Go to Google Analytics Console (https://analytics.google.com/analytics/web/) \n2. At the top left corner check that you're using the right property\n  - Given that you have already setup Firebase platforms (as described above) make sure to choose the configure property in order to have data in one place for all platforms\n3. Click Admin (gear icon at the bottom left) -\u003e Data Stream -\u003e `Add stream` button -\u003e `Web`\n  - Enter any URL and choose stream name (e.g. 'Windows-Linux')\n  - Skip installation instructions\n  - Copy `Measurement ID`\n  - Click `Measurement Protocol API secrets` in the same view below. Create a new API secret and copy it.\n  - Both values must be provided to `init()` method to get Measurement Protocol working (see next section)\n\n\n# Using Ambilytics in your app\n\n1. Add `firebase_core` and `ambilytics` packages to `dependencies` section of `pubspec.yaml`:\n```yaml\ndependencies:\ndependencies:\n  flutter:\n    sdk: flutter  \n  cupertino_icons: ^1.0.2\n  firebase_core:\n  ambilytics:\n```\n2. Import Ambilytics:\n```dart\nimport 'package:ambilytics/ambilytics.dart' as ambilytics;\n```\n3. In the `main` function add initialization call:\n```dart\nvoid main() async {\n  // This one\n  await ambilytics.initAnalytics(\n      measurementId: 'G-6R363DDKTZ',\n      apiSecret: 'uzUv6h_iRS6hEt_sIVtTTA',\n      firebaseOptions: DefaultFirebaseOptions.currentPlatform);\n  runApp(const MyApp());\n}\n```\n- it's assumed that you have `firebase_options.dart` generated by `flutterfire` (see above) with `DefaultFirebaseOptions` class defined there\n- you've setup Measurement Protocol as described above provided correct `measurementId` and `apiSecret`\n4. If you want to track navigation events, add navigator observer to `MaterialApp`, e.g.:\n\n```dart\nclass MyApp extends StatelessWidget {\n  const MyApp({super.key});\n\n  @override\n  Widget build(BuildContext context) {\n    return MaterialApp(\n      title: 'Flutter Demo',\n      theme: ThemeData(\n        primarySwatch: Colors.blue,\n      ),\n      // Here\n      navigatorObservers: ambilytics.isAmbilyticsInitialized\n          ? [\n              ambilytics.AmbilyticsObserver(\n                  routeFilter: ambilytics.anyRouteFilter,\n                  alwaySendScreenViewCust: true)\n            ]\n          : [],\n      routes: {\n        '/': (context) =\u003e HomeScreen(\n              title: 'Home',\n              analyticsError: ambilytics.initError,\n            ),\n        '/color/red': (context) =\u003e const ColorScreen(),\n        '/color/yellow': (context) =\u003e const ColorScreen()\n      },\n    );\n  }\n}\n```\n5. You can send custom events via Ambilytics `sendEvent` function:\n```dart\n  void _incrementCounter() {\n    setState(() {\n      _counter++;\n      // Here\n      ambilytics.sendEvent(counterClicked, null);\n    });\n  }\n```\n\n# Using Reports\n\nThe reports can be seen in both Google Analytics Console (https://analytics.google.com/analytics/web/) and Firebase Console (https://console.firebase.google.com/).\n\n## Ambilytics custom events\n\nThe package automatically sends 2 custom events:\n- `app_launch` - sent upon initialization of Ambilytics. Contains `platform` parameters with the name of the platform where the app is built.\n- `screen_view_cust` - sent via navigation observer upon navigation events (such as pushing a new route via Navigator API). Since Google Analytics doesn't allow sending predefined events (such as `screen_view`) via its' `logEvent()` this event is used for Windows and Linux as substitute for standard event. The events has `screen_name` which is set to route name (`Route.settings.name`)\n  - You can use `AmbilyticsObserver.alwaySendScreenViewCust` parameter to have this custom event sent along with standard `screen_view` with any of the Firebase platforms\n\n\n## Seeing custom events' params\n\nParameters of custom events (the above 2 and all sent via `sendEvent()`) by default can only be seen in Realtime view. For other reports a custom dimension must be created:\n- Admin (gear icon at the bottom left) -\u003e Custom definitions -\u003e Create custom dimensions -\u003e type in dimension name and param -\u003e go to reports and pick custom dimension.\n  - Note that you don't have to type in event name, just a description name of dimension AND exact name of parameter\n- Make sure you add dimensions for params of  `app_launch` and `screen_view_cust`\n  - E.g. create `app_launch_platform` dimension with `platform` param and `screen_view_cust_screen` with `screen_name` parameter\n\nQuote from Google docs: \n*To see the event parameter values, you must create a custom dimension or metric for each event parameter. Once Analytics processes the custom dimension or metric, you can add it to your custom reports, audiences, explorations, and segments, and as secondary dimensions in standard reports.\"*\n\nNote that up to 1 day might be required to get updated data in reports outside Realtime view.\n\nAfter that you should be able to see custom events and their params in reports, e.g. pick `Engagement -\u003e Events` and click + sign in the `Event name` column and choose `Custom -\u003e [Dimension you created]`\n\n# Known issues/Troubleshooting\n\n## 1. Can't build macOS/iOS project with 'Error run pod install' or alike\nIn terminal go to macOS or iOS folder, remove `Podfile.lock` and run `pod repo update`\n\n## 2. Android build fails (:app:mapReleaseSourceSetPaths)\nIf you get error \n```\nExecution failed for task ':app:mapReleaseSourceSetPaths'.\n\u003e Error while evaluating property 'extraGeneratedResDir' of task ':app:mapReleaseSourceSetPaths'\n```\n\nGo to `android/build.gradle` and update `com.google.gms:google-services` version, e.g.:\n```gradle\n    dependencies {\n        classpath 'com.android.tools.build:gradle:7.3.0'\n        // START: FlutterFire Configuration\n        classpath 'com.google.gms:google-services:4.3.15'\n        // END: FlutterFire Configuration\n        classpath \"org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version\"\n    }\n```\n\n## 3. Android build fails (minSdkVersion mismatch)\nGo to `android/app/build.gradle` and change `minSdkVersion` version from `flutter.minSdkVersion` to `19`.\n\n## 4. No data in Google Analytics reports\nAll reports outside `Realtime` can take up to a day to be in sync\n\n## 5. No data in Realtime reports (on Android, iOS)\nFor mobile platforms (Android, iOS) Firebase Analytics uploads/processes data in batches, i.e. it takes some time to collect and than send and display it (presumably for battery saving). As a result you get jagged events (i.e. some come right away, some take time).\n\n## 5. No data in reports from macOS clients\nCheck the above manual for *Fix macOS* and update `DebugProfile.entitlements` and `Release.entitlements`\n\n## 6. `A Firebase App named \"[DEFAULT]\" already exists` error\nLikely reason for that is that you already used FirebaseAnalytics with configured native projects and started using FirebaseOptions.\nYou can try deleting `android/app/src/google-services.json`, `ios/Runner/GoogleService-Info.plist` and `macos/Runner/GoogleService-Info.plist` files and rerun `flutterfire configure`\n\n## 7. Error initialising Firebase on a Linux or Windows environment\nYou may see this error: `Unhandled Exception: Unsupported operation: DefaultFirebaseOptions are not supported for this platform.`\n\nThis occurs when you build with the `firebaseOptions` in the config when building to Linux or Windows. You could conditionally add this config option if you do need to build to different environments if required.\n\nHowever, Firebase config is not necessary, so perhaps if you want to use the Measurement Protocol exclusively or you are only building to a Linux and Windows environment, you can leave out the `firebaseOptions` config entirely...\n\n```dart\nambilytics.initAnalytics(\n    measurementId: 'G-6R363DDKTZ',\n    apiSecret: 'uzUv6h_iRS6hEt_sIVtTTA',\n);\n```","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmaxim-saplin%2Fambilytics","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmaxim-saplin%2Fambilytics","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmaxim-saplin%2Fambilytics/lists"}