Releases: snowplow/snowplow-android-tracker
Version 5.0.0
We are very excited to announce the v5 of the Snowplow Android tracker. The tracker is now written in Kotlin, rather than Java!
We've added a new plugins
feature so you can provide custom tracker plugins to intercept tracked events. Plugins provide callbacks that can enrich events with additional entities, and inspect tracked events. The following snippet gives an overview of how to use plugins.
// identifier needs to uniquely identify the plugin
val plugin = PluginConfiguration("myPlugin")
// entities closure can return context entities to enrich events
// the list of schemas to call the closure for is optional (it will be called for all events if null)
plugin.entities(listOf("iglu:...")) {
return [
SelfDescribingJson(schema: "iglu:xx", andData: ["yy": true])
]
}
// after track callback called on a background thread to inspect final tracked events
// one can also supply a list of schemas to call the closure only for specific events
plugin.afterTrack {
print("Tracked event with $event.entities.size entities")
}
// the plugin is supplied to the tracker as a configuration
val tracker = Snowplow.createTracker(
context = context,
namespace = "ns",
network = networkConfig,
plugin
)
// one can inspect the enabled plugins and get the list of their identifiers
val pluginIdentifiers = tracker.plugins.identifiers
// add additional plugins (using PluginConfiguration as above)
tracker.plugins.addPlugin(otherPlugin)
// remove registered plugins by their identifiers
tracker.plugins.removePlugin("myPlugin")
There's a new demo app using Jetpack Compose, to help you instrument the Android tracker using Compose. On top of that, the API and Snowplow documentation has been overhauled and improved.
The API is pretty much unchanged since v4: read more in the migration guide.
CHANGELOG
New features
- Add Jetpack Compose demo app (#586)
- Add ability to provide custom tracker plugins to inspect and enrich tracked events (#574)
Under the hood
- Add default POST argument to basic createTracker method (#592)
- Reintroduce customContexts as a Java field and return a mutable list from entities in events (#590)
- Add plugin example to Kotlin demo (#593)
- Use Dokka for API docs (#591)
- Upgrade Gradle to 7.6 and lower minSdkVersion requirement to 21 (#587 and #585)
- Update copyrights to 2023 (#579)
- Refactor event interface and rename contexts to entities (#573)
- Migrate internal classes to Kotlin (#564)
- Migrate published API to Kotlin (#561)
Version 5.0.0-beta.2
This is the third pre-release of the upcoming version 5 of the Android tracker written in Kotlin. This beta release upgrades the Gradle version to 7.6 as well as other tracker dependencies. Additionally, the minimum SDK version has been lowered to version 21 as in the v4 tracker.
Enhancements
Version 4.1.2
This patch release fixes a bug that caused null pointer exceptions when accessing session information before it was initialised or when tracking events when session was not yet initialised.
Bug fixes
- Fix crash with null pointer when accessing session (#581)
Version 5.0.0-beta.1
This is the second pre-release of the upcoming version 5 of the Android tracker written in Kotlin. This beta release brings new features as well as refactoring the tracker internals. All of the code is now in Kotlin.
The headline feature is the ability to provide custom tracker plugins to intercept tracked events. Plugins provide callbacks that can enrich events with additional entities and inspect tracked events. See this snippet for a glimpse of a tracker plugin:
// identifier needs to uniquely identify the plugin
val plugin = PluginConfiguration("myPlugin")
// entities closure can return context entities to enrich events
// the list of schemas to call the closure for is optional (it will be called for all events if null)
plugin.entities(listOf("iglu:...")) {
return [
SelfDescribingJson(schema: "iglu:xx", andData: ["yy": true])
]
}
// after track callback called on a background thread to inspect final tracked events
// one can also supply a list of schemas to call the closure only for specific events
plugin.afterTrack {
print("Tracked event with $event.entities.size entities")
}
// the plugin is supplied to the tracker as a configuration
val tracker = Snowplow.createTracker(
context = context,
namespace = "ns",
network = networkConfig,
plugin
)
Enhancements
- Add ability to provide custom tracker plugins to inspect and enrich tracked events (#574)
Under the hood
Version 4.1.1
This release fixes a bug where the session user ID was truncated on certain phones.
CHANGELOG
Hardcode the anonymised session user ID (#566)
Version 5.0.0-alpha.1
We are excited to announce our plans for the version 5 of our Android Tracker. In addition, we are releasing the first alpha pre-release of the v5 tracker.
The major enhancement is the modernization of the trackers – we will migrate the Android tracker from Java to Kotlin. This opens up a range of exciting new possibilities for the tracker. It will provide APIs that work better with modern Kotlin apps. The modern programming language will enable a safer implementation of core features of the tracker. Finally, it will enable us to simplify the tracker code and build system, making it easier to contribute to and maintain the trackers moving forward.
Version 5 will also bring other new features to the trackers that we are already excited about. We will announce these as we progress on them and publish next pre-releases. Stay tuned!
If you are interested in testing the experimental alpha 1 release, we would appreciate your feedback! In this version, the published API has been translated to Kotlin, while the internal Core classes remain as Java. We'll be translating the remaining code in the next release.
CHANGELOG
Migrate published API to Kotlin (#561)
Version 4.1.0
This release improves the anonymous tracking functionality by anonymising additional properties in Subject and Session. In Subject, the manually set userId
, domainUserId
, networkUserId
, and ipAddress
are now anonymised. In Session, previousSessionId
is anonymised to prevent stitching independent anonymous sessions.
Now the tracker also sets the page_referrer
and page_url
atomic event properties for Screen View events. This improves compatibility with the Referer parser enrichment.
Enhancements
- Anonymise previous session ID and user identifiers in subject when user anonymisation is enabled (#549)
- Add DeepLink entity referrer and url to atomic properties in ScreenView events (#553)
- Log an error when recreating tracker after being removed (#548)
Bug fixes
- Fix serialization of session timeouts in remote configuration cache (#547)
- Expose public constructor for ConfigurationBundle (#550)
Under the hood
- Fix links in README (#557)
Version 4.0.0
These releases bring two exciting new features to the trackers: support for hybrid apps, and anonymous tracking.
Support for hybrid apps enables tracking Snowplow events in Web views. The iOS and Android trackers communicate with the WebView tracker that can be installed in Web apps to track events. This enables events to share the same session and context entities as events tracked using the native mobile trackers!
Anonymous tracking is a tracker feature that enables anonymising various user and session identifiers to support user privacy in case consent for tracking the identifiers is not given. Similar to the JavaScript tracker, the mobile trackers let you configure user anonymisation (using the userAnonymisation
flag in TrackerConfiguration
) to anonymise user identifiers in session and platform context and server anonymisation (using the serverAnonymisation
flag in EmitterConfiguration
) to anonymise the network_userid
and user_ipaddress
properties assigned by the Collector.
Other changes in the trackers include improvements in remote configuration that now supports switching between multiple remote configuration endpoints and gives feedback of where the configuration was retrieved from (from cache, default values or fetched over network). Additionally, the tracker.track(event)
function now returns the event ID.
We are also excited to announce major improvements to the documentation that now gives more guidance on how to make use of all the tracker features!
CHANGELOG
Enhancements:
- Add interface to subscribe for events tracked in Web views (#531)
- Add anonymous tracking features (#540)
- Return tracked event ID from the track method (#544)
- Extend the onSuccess callback when setting up remote configuration to pass configuration state (#694)
Bug fixes:
- Do not resume remote configuration from cache in case it has different endpoint (#533)
Under the hood:
- Fix default session timeout values to 30 minutes everywhere (#542)
Version 3.2.1
This fixes a bug that affected datetimes in the session entity. The user device locale was being used for creating dates, sometimes resulting in non-Arabic numerals, e.g. Eastern Arabic numerals. The session entity now only uses English ("en") numerals.
CHANGELOG
Bug fix:
Ensure english numerals are used in datetimes (#537)
Version 3.2.0
The tracker now makes use of the client_session
schema version 1-0-2, which adds two new properties to the session context entity – eventIndex
(index of the event in the session) and firstEventTimestamp
(timestamp of the first event in the session). The event index property is useful for ordering events as they were tracked.
The release also changes the behaviour for 5 HTTP status codes (400, 401, 403, 410, and 422) that, when received in response from the Collector, will now cause the tracker not to retry sending events (i.e., drop the events). Requests with all other 3xx, 4xx, and 5xx status codes are retried. The set of status codes for which events should be retried or not is customizable in EmitterConfiguration
. The following shows the configuration in the Android tracker:
EmitterConfiguration emitterConfiguration = new EmitterConfiguration();
Map<Integer, Boolean> retryRules = new HashMap<>();
retryRules.put(403, true); // retry for the 403 HTTP status code
emitterConfiguration.setCustomRetryForStatusCodes(retryRules);
Finally, the release adds support for storing cookies set by the Collector. This means that the network_userid
property set by the Collector is now kept consistent among events tracked by the same tracker. Cookies are stored in shared preferences with an option to provide a custom cookie jar.
CHANGELOG
Features:
- Add eventIndex and firstEventTimestamp properties to client sessions (#517)
- Add a customizable set of failure HTTP status codes for which collector requests should not be retried (#518)
- Add support for storing cookies in NetworkConnection (#519)
Under the hood: