Skip to content

Commit c783068

Browse files
authored
Add organic install tracking and upgrade to Java 17
- Add organic install detection in AppsflyerDestination by checking af_status field from AppsFlyer conversion data - Track "Organic Install" event for organic installs - Upgrade build to Java 17 to match AppsFlyer - Add devbox configuration
1 parent 19d4574 commit c783068

12 files changed

Lines changed: 295 additions & 62 deletions

File tree

.github/workflows/build.yml

Lines changed: 10 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -7,33 +7,19 @@ on:
77
branches: [ main ]
88
workflow_dispatch:
99

10-
jobs:
10+
concurrency:
11+
group: ${{ github.workflow }}-${{ github.ref }}
12+
cancel-in-progress: true
1113

12-
cancel_previous:
13-
permissions: write-all
14-
runs-on: ubuntu-latest
15-
steps:
16-
- uses: styfle/cancel-workflow-action@0.9.1
17-
with:
18-
workflow_id: ${{ github.event.workflow.id }}
19-
14+
jobs:
2015
build:
21-
22-
needs: cancel_previous
2316
runs-on: ubuntu-latest
2417

2518
steps:
26-
- uses: actions/checkout@v2
27-
- name: Grant execute permission for gradlew
28-
run: chmod +x gradlew
29-
- name: cache gradle dependencies
30-
uses: actions/cache@v4
19+
- uses: actions/checkout@v4
20+
- name: Install devbox
21+
uses: jetify-com/devbox-install-action@v0.14.0
3122
with:
32-
path: |
33-
~/.gradle/caches
34-
~/.gradle/wrapper
35-
key: ${{ runner.os }}-gradle-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}
36-
restore-keys: |
37-
${{ runner.os }}-gradle-
38-
- name: Run Tests
39-
run: ./gradlew check
23+
enable-cache: true
24+
- name: Run checks
25+
run: devbox run check

.github/workflows/release.yml

Lines changed: 9 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -11,39 +11,31 @@ jobs:
1111
runs-on: ubuntu-latest
1212
environment: deployment
1313
steps:
14-
- uses: actions/checkout@v2
14+
- uses: actions/checkout@v4
1515
- name: Get tag
1616
id: vars
17-
run: echo ::set-output name=tag::${GITHUB_REF#refs/*/}
17+
run: echo "tag=${GITHUB_REF#refs/*/}" >> "$GITHUB_OUTPUT"
1818
- name: Verify tag
1919
run: |
2020
VERSION=$(grep VERSION_NAME gradle.properties | awk -F= '{ print $2 }' | sed "s/-SNAPSHOT//")
2121
if [ "${{ steps.vars.outputs.tag }}" != "$VERSION" ]; then {
2222
echo "Tag ${{ steps.vars.outputs.tag }} does not match the package version ($VERSION)"
2323
exit 1
2424
} fi
25-
26-
- name: Grant execute permission for gradlew
27-
run: chmod +x gradlew
28-
- name: cache gradle dependencies
29-
uses: actions/cache@v4
25+
- name: Install devbox
26+
uses: jetify-com/devbox-install-action@v0.14.0
3027
with:
31-
path: |
32-
~/.gradle/caches
33-
~/.gradle/wrapper
34-
key: ${{ runner.os }}-gradle-core-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}
35-
restore-keys: |
36-
${{ runner.os }}-gradle-core-
37-
- name: Publush release to sonatype
38-
run: ./gradlew publishToSonatype -Prelease closeAndReleaseSonatypeStagingRepository
28+
enable-cache: true
29+
- name: Publish release to sonatype
30+
run: devbox run publish-release
3931
env:
4032
SIGNING_KEY_ID: ${{ secrets.SIGNING_KEY_ID }}
4133
SIGNING_KEY_PASSWORD: ${{ secrets.SIGNING_KEY_PASSWORD }}
4234
ORG_GRADLE_PROJECT_sonatypeUsername: ${{ secrets.NEXUS_USERNAME }}
4335
ORG_GRADLE_PROJECT_sonatypePassword: ${{ secrets.NEXUS_PASSWORD }}
4436
SIGNING_PRIVATE_KEY_BASE64: ${{ secrets.SIGNING_PRIVATE_KEY_BASE64 }}
4537

46-
- name: create release
38+
- name: Create release
4739
run: |
4840
curl \
4941
-X POST \
@@ -52,4 +44,4 @@ jobs:
5244
-d '{"tag_name": "${{ env.RELEASE_VERSION }}", "name": "${{ env.RELEASE_VERSION }}", "body": "Release of version ${{ env.RELEASE_VERSION }}", "draft": false, "prerelease": false, "generate_release_notes": true}'
5345
env:
5446
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
55-
RELEASE_VERSION: ${{ steps.vars.outputs.tag }}
47+
RELEASE_VERSION: ${{ steps.vars.outputs.tag }}

.github/workflows/snapshot.yml

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -9,23 +9,16 @@ jobs:
99
runs-on: ubuntu-latest
1010
environment: deployment
1111
steps:
12-
- uses: actions/checkout@v2
13-
- name: Grant execute permission for gradlew
14-
run: chmod +x gradlew
15-
- name: cache gradle dependencies
16-
uses: actions/cache@v4
12+
- uses: actions/checkout@v4
13+
- name: Install devbox
14+
uses: jetify-com/devbox-install-action@v0.14.0
1715
with:
18-
path: |
19-
~/.gradle/caches
20-
~/.gradle/wrapper
21-
key: ${{ runner.os }}-gradle-core-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }}
22-
restore-keys: |
23-
${{ runner.os }}-gradle-core-
24-
- name: Publush snapshot to sonatype
25-
run: ./gradlew publishToSonatype
16+
enable-cache: true
17+
- name: Publish snapshot to sonatype
18+
run: devbox run publish-snapshot
2619
env:
2720
SIGNING_KEY_ID: ${{ secrets.SIGNING_KEY_ID }}
2821
SIGNING_KEY_PASSWORD: ${{ secrets.SIGNING_KEY_PASSWORD }}
2922
ORG_GRADLE_PROJECT_sonatypeUsername: ${{ secrets.NEXUS_USERNAME }}
3023
ORG_GRADLE_PROJECT_sonatypePassword: ${{ secrets.NEXUS_PASSWORD }}
31-
SIGNING_PRIVATE_KEY_BASE64: ${{ secrets.SIGNING_PRIVATE_KEY_BASE64 }}
24+
SIGNING_PRIVATE_KEY_BASE64: ${{ secrets.SIGNING_PRIVATE_KEY_BASE64 }}

build.gradle.kts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,12 @@ plugins {
1111
// Apply the java-library plugin for API and implementation separation.
1212
`java-library`
1313
id("io.github.gradle-nexus.publish-plugin") version "1.1.0"
14+
}
1415

16+
java {
17+
toolchain {
18+
languageVersion.set(JavaLanguageVersion.of(17))
19+
}
1520
}
1621

1722
buildscript {

devbox.json

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
{
2+
"$schema": "https://raw.githubusercontent.com/jetify-com/devbox/0.14.2/.schema/devbox.schema.json",
3+
"packages": {
4+
"jdk17": "latest",
5+
"gradle": "latest",
6+
"path:./nix#android-sdk": ""
7+
},
8+
"shell": {
9+
"init_hook": [
10+
"export ANDROID_SDK_ROOT=\"$(nix --extra-experimental-features 'nix-command flakes' eval --raw 'path:./nix#android-sdk.outPath' 2>/dev/null)/libexec/android-sdk\"",
11+
"export ANDROID_HOME=\"$ANDROID_SDK_ROOT\""
12+
],
13+
"scripts": {
14+
"test": [
15+
"./gradlew :lib:testDebugUnitTest --no-daemon"
16+
],
17+
"build": [
18+
"./gradlew build --no-daemon"
19+
],
20+
"clean": [
21+
"./gradlew clean --no-daemon"
22+
],
23+
"check": [
24+
"./gradlew check --no-daemon"
25+
],
26+
"publish-release": [
27+
"./gradlew publishToSonatype -Prelease closeAndReleaseSonatypeStagingRepository --no-daemon"
28+
],
29+
"publish-snapshot": [
30+
"./gradlew publishToSonatype --no-daemon"
31+
],
32+
"info": [
33+
"echo \"JAVA_HOME: $JAVA_HOME\"",
34+
"echo \"ANDROID_SDK_ROOT: $ANDROID_SDK_ROOT\"",
35+
"java -version",
36+
"./gradlew -v"
37+
]
38+
}
39+
}
40+
}

devbox.lock

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
{
2+
"lockfile_version": "1",
3+
"packages": {
4+
"github:NixOS/nixpkgs/nixpkgs-unstable": {
5+
"last_modified": "2026-02-04T01:49:30Z",
6+
"resolved": "github:NixOS/nixpkgs/aa290c9891fa4ebe88f8889e59633d20cc06a5f2?lastModified=1770169770"
7+
},
8+
"gradle@latest": {
9+
"last_modified": "2026-01-26T09:54:05Z",
10+
"plugin_version": "0.0.1",
11+
"resolved": "github:NixOS/nixpkgs/5b265bda51b42a2a85af0a543c3e57b778b01b7d#gradle",
12+
"source": "devbox-search",
13+
"version": "8.14.4",
14+
"systems": {
15+
"aarch64-darwin": {
16+
"outputs": [
17+
{
18+
"name": "out",
19+
"path": "/nix/store/yb98qaa8if1gvdihj9vngyv822kqs88v-gradle-8.14.4",
20+
"default": true
21+
}
22+
],
23+
"store_path": "/nix/store/yb98qaa8if1gvdihj9vngyv822kqs88v-gradle-8.14.4"
24+
},
25+
"aarch64-linux": {
26+
"outputs": [
27+
{
28+
"name": "out",
29+
"path": "/nix/store/xbn16nkgbaj09mf3vgzs7y582m67bm9s-gradle-8.14.4",
30+
"default": true
31+
}
32+
],
33+
"store_path": "/nix/store/xbn16nkgbaj09mf3vgzs7y582m67bm9s-gradle-8.14.4"
34+
},
35+
"x86_64-darwin": {
36+
"outputs": [
37+
{
38+
"name": "out",
39+
"path": "/nix/store/m0xaca5z53sg9n6jqlkvm6cq0cn7ny28-gradle-8.14.4",
40+
"default": true
41+
}
42+
],
43+
"store_path": "/nix/store/m0xaca5z53sg9n6jqlkvm6cq0cn7ny28-gradle-8.14.4"
44+
},
45+
"x86_64-linux": {
46+
"outputs": [
47+
{
48+
"name": "out",
49+
"path": "/nix/store/7nhijwwp2cdwnj2f19c5qdp2igf6cqb9-gradle-8.14.4",
50+
"default": true
51+
}
52+
],
53+
"store_path": "/nix/store/7nhijwwp2cdwnj2f19c5qdp2igf6cqb9-gradle-8.14.4"
54+
}
55+
}
56+
},
57+
"jdk17@latest": {
58+
"last_modified": "2025-10-22T20:59:19Z",
59+
"resolved": "github:NixOS/nixpkgs/01b6809f7f9d1183a2b3e081f0a1e6f8f415cb09#jdk17",
60+
"source": "devbox-search",
61+
"version": "17.0.12",
62+
"systems": {
63+
"aarch64-darwin": {
64+
"outputs": [
65+
{
66+
"name": "out",
67+
"path": "/nix/store/hlm8a8cnp4hm8xkg0a2yy4kv7cq44jii-zulu-ca-jdk-17.0.12",
68+
"default": true
69+
}
70+
],
71+
"store_path": "/nix/store/hlm8a8cnp4hm8xkg0a2yy4kv7cq44jii-zulu-ca-jdk-17.0.12"
72+
},
73+
"x86_64-darwin": {
74+
"outputs": [
75+
{
76+
"name": "out",
77+
"path": "/nix/store/i4zgq9685y6284hbf5a7ac9ysb88dvlz-zulu-ca-jdk-17.0.12",
78+
"default": true
79+
}
80+
],
81+
"store_path": "/nix/store/i4zgq9685y6284hbf5a7ac9ysb88dvlz-zulu-ca-jdk-17.0.12"
82+
}
83+
}
84+
}
85+
}
86+
}

gradle.properties

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,17 +6,21 @@
66
# http://www.gradle.org/docs/current/userguide/build_environment.html
77
# Specifies the JVM arguments used for the daemon process.
88
# The setting is particularly useful for tweaking memory settings.
9-
org.gradle.jvmargs=-Xmx2048m -Dfile.encoding=UTF-8
9+
org.gradle.jvmargs=-Xmx2048m -Dfile.encoding=UTF-8 -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError
1010
# When configured, Gradle will run in incubating parallel mode.
1111
# This option should only be used with decoupled projects. More details, visit
1212
# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
13-
# org.gradle.parallel=true
13+
org.gradle.parallel=true
1414
# AndroidX package structure to make it clearer which packages are bundled with the
1515
# Android operating system, and which are packaged with your app"s APK
1616
# https://developer.android.com/topic/libraries/support-library/androidx-rn
1717
android.useAndroidX=true
1818
# Automatically convert third-party libraries to use AndroidX
1919
android.enableJetifier=true
20+
android.suppressUnsupportedCompileSdk=33
21+
22+
# Java 17 configuration
23+
org.gradle.java.installations.auto-detect=false
2024
# Kotlin code style for this project: "official" or "obsolete":
2125
kotlin.code.style=official
2226

lib/build.gradle.kts

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,11 @@ android {
2929
}
3030
}
3131
compileOptions {
32-
sourceCompatibility = JavaVersion.VERSION_1_8
33-
targetCompatibility = JavaVersion.VERSION_1_8
32+
sourceCompatibility = JavaVersion.VERSION_17
33+
targetCompatibility = JavaVersion.VERSION_17
3434
}
3535
kotlinOptions {
36-
jvmTarget = "1.8"
36+
jvmTarget = "17"
3737
}
3838
}
3939

@@ -80,6 +80,18 @@ dependencies {
8080

8181
tasks.withType<Test> {
8282
useJUnitPlatform()
83+
jvmArgs = listOf(
84+
"--add-opens", "java.base/java.lang=ALL-UNNAMED",
85+
"--add-opens", "java.base/java.util=ALL-UNNAMED"
86+
)
87+
testLogging {
88+
events("passed", "skipped", "failed")
89+
}
90+
91+
// Ensure tests use Java 17
92+
javaLauncher.set(javaToolchains.launcherFor {
93+
languageVersion.set(JavaLanguageVersion.of(17))
94+
})
8395
}
8496

8597
// required for mvn-publish

lib/src/main/java/com/segment/analytics/kotlin/destinations/appsflyer/AppsflyerDestination.kt

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,17 @@ class AppsFlyerDestination(
160160
inner class ConversionListener : AppsFlyerConversionListener {
161161
override fun onConversionDataSuccess(conversionData: Map<String, Any>) {
162162
if (!getFlag(CONV_KEY)) {
163-
trackInstallAttributed(conversionData)
163+
// Check for install type (organic vs non-organic)
164+
val status = conversionData["af_status"] as? String
165+
166+
if (status == "Non-organic") {
167+
// Track attributed install
168+
trackInstallAttributed(conversionData)
169+
} else {
170+
// Track organic install (similar to Swift implementation)
171+
analytics.track("Organic Install")
172+
}
173+
164174
setFlag(CONV_KEY, true)
165175
}
166176
conversionListener?.onConversionDataSuccess(conversionData)

0 commit comments

Comments
 (0)