Skip to content

Commit 2dcaea8

Browse files
authored
Merge 60e189c into ba01011
2 parents ba01011 + 60e189c commit 2dcaea8

16 files changed

Lines changed: 91 additions & 119 deletions

File tree

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@
1313
### Improvements
1414

1515
- Reduce boxing to improve performance ([#5523](https://github.com/getsentry/sentry-java/pull/5523), [#5527](https://github.com/getsentry/sentry-java/pull/5527), [#5551](https://github.com/getsentry/sentry-java/pull/5551))
16+
- Replace `Date` with a unix timestamp in `SentryNanotimeDate` to improve performance ([#5550](https://github.com/getsentry/sentry-java/pull/5550))
17+
- `SentryNanotimeDate` is now marked `@ApiStatus.Internal`. Its constructor changed from `(Date, long)` to `(long unixDate, long nanos)`, where `unixDate` is milliseconds since the epoch. Behavior is unchanged as `Date.getTime()` already returns epoch millis.
1618

1719
### Dependencies
1820

sentry-android-core/src/main/java/io/sentry/android/core/ActivityLifecycleIntegration.java

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,6 @@
4545
import java.io.IOException;
4646
import java.lang.ref.WeakReference;
4747
import java.util.Collections;
48-
import java.util.Date;
4948
import java.util.Map;
5049
import java.util.WeakHashMap;
5150
import java.util.concurrent.Future;
@@ -94,7 +93,7 @@ public final class ActivityLifecycleIntegration
9493
private final @NotNull WeakHashMap<Activity, ISpan> ttfdSpanMap = new WeakHashMap<>();
9594
private final @NotNull WeakHashMap<Activity, ActivityLifecycleSpanHelper> activitySpanHelpers =
9695
new WeakHashMap<>();
97-
private @NotNull SentryDate lastPausedTime = new SentryNanotimeDate(new Date(0), 0);
96+
private @NotNull SentryDate lastPausedTime = new SentryNanotimeDate(0, 0);
9897
private @Nullable Future<?> ttfdAutoCloseFuture = null;
9998

10099
// WeakHashMap isn't thread safe but ActivityLifecycleCallbacks is only called from the
@@ -729,7 +728,7 @@ public void onActivityDestroyed(final @NotNull Activity activity) {
729728

730729
private void clear() {
731730
firstActivityCreated = false;
732-
lastPausedTime = new SentryNanotimeDate(new Date(0), 0);
731+
lastPausedTime = new SentryNanotimeDate(0, 0);
733732
activitySpanHelpers.clear();
734733
}
735734

sentry-android-core/src/main/java/io/sentry/android/core/SpanFrameMetricsCollector.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313
import io.sentry.android.core.internal.util.SentryFrameMetricsCollector;
1414
import io.sentry.protocol.MeasurementValue;
1515
import io.sentry.util.AutoClosableReentrantLock;
16-
import java.util.Date;
1716
import java.util.Iterator;
1817
import java.util.SortedSet;
1918
import java.util.TreeSet;
@@ -33,7 +32,7 @@ public class SpanFrameMetricsCollector
3332
// grow indefinitely in case of a long running span
3433
private static final int MAX_FRAMES_COUNT = 3600;
3534
private static final long ONE_SECOND_NANOS = TimeUnit.SECONDS.toNanos(1);
36-
private static final SentryNanotimeDate EMPTY_NANO_TIME = new SentryNanotimeDate(new Date(0), 0);
35+
private static final SentryNanotimeDate EMPTY_NANO_TIME = new SentryNanotimeDate(0, 0);
3736

3837
private final boolean enabled;
3938
protected final @NotNull AutoClosableReentrantLock lock = new AutoClosableReentrantLock();

sentry-android-core/src/test/java/io/sentry/android/core/ActivityLifecycleIntegrationTest.kt

Lines changed: 33 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,6 @@ import io.sentry.protocol.SentryId
4141
import io.sentry.protocol.TransactionNameSource
4242
import io.sentry.test.DeferredExecutorService
4343
import io.sentry.test.getProperty
44-
import java.util.Date
4544
import java.util.concurrent.Future
4645
import java.util.concurrent.TimeUnit
4746
import kotlin.test.AfterTest
@@ -936,7 +935,7 @@ class ActivityLifecycleIntegrationTest {
936935
sut.register(fixture.scopes, fixture.options)
937936
sut.setFirstActivityCreated(false)
938937

939-
val date = SentryNanotimeDate(Date(1), 0)
938+
val date = SentryNanotimeDate(1, 0)
940939
setAppStartTime(date)
941940
fixture.options.dateProvider = SentryDateProvider { date }
942941

@@ -961,7 +960,7 @@ class ActivityLifecycleIntegrationTest {
961960
sut.register(fixture.scopes, fixture.options)
962961
sut.setFirstActivityCreated(false)
963962

964-
val date = SentryNanotimeDate(Date(1), 0)
963+
val date = SentryNanotimeDate(1, 0)
965964
setAppStartTime(date)
966965

967966
val activity = mock<Activity>()
@@ -984,8 +983,8 @@ class ActivityLifecycleIntegrationTest {
984983
sut.register(fixture.scopes, fixture.options)
985984
sut.setFirstActivityCreated(false)
986985

987-
val date = SentryNanotimeDate(Date(1), 0)
988-
val date2 = SentryNanotimeDate(Date(2), 2)
986+
val date = SentryNanotimeDate(1, 0)
987+
val date2 = SentryNanotimeDate(2, 2)
989988
setAppStartTime(date)
990989

991990
val activity = mock<Activity>()
@@ -1011,7 +1010,7 @@ class ActivityLifecycleIntegrationTest {
10111010
val sut = fixture.getSut { it.tracesSampleRate = 1.0 }
10121011
sut.register(fixture.scopes, fixture.options)
10131012
sut.setFirstActivityCreated(true)
1014-
val date = SentryNanotimeDate(Date(1), 0)
1013+
val date = SentryNanotimeDate(1, 0)
10151014
setAppStartTime(date)
10161015

10171016
val activity = mock<Activity>()
@@ -1030,8 +1029,8 @@ class ActivityLifecycleIntegrationTest {
10301029
sut.setFirstActivityCreated(false)
10311030

10321031
// usually set by SentryPerformanceProvider
1033-
val date = SentryNanotimeDate(Date(1), 0)
1034-
val date2 = SentryNanotimeDate(Date(2), 2)
1032+
val date = SentryNanotimeDate(1, 0)
1033+
val date2 = SentryNanotimeDate(2, 2)
10351034

10361035
val activity = mock<Activity>()
10371036
// Activity onCreate date will be used
@@ -1056,7 +1055,7 @@ class ActivityLifecycleIntegrationTest {
10561055
sut.register(fixture.scopes, fixture.options)
10571056

10581057
// usually set by SentryPerformanceProvider
1059-
val date = SentryNanotimeDate(Date(1), 0)
1058+
val date = SentryNanotimeDate(1, 0)
10601059
setAppStartTime(date)
10611060

10621061
val activity = mock<Activity>()
@@ -1080,7 +1079,7 @@ class ActivityLifecycleIntegrationTest {
10801079
sut.register(fixture.scopes, fixture.options)
10811080

10821081
// usually set by SentryPerformanceProvider
1083-
val startDate = SentryNanotimeDate(Date(1), 0)
1082+
val startDate = SentryNanotimeDate(1, 0)
10841083
setAppStartTime(startDate)
10851084
val appStartMetrics = AppStartMetrics.getInstance()
10861085
appStartMetrics.appStartType = AppStartType.WARM
@@ -1113,9 +1112,9 @@ class ActivityLifecycleIntegrationTest {
11131112
it.isEnableStandaloneAppStartTracing = true
11141113
}
11151114
sut.register(fixture.scopes, fixture.options)
1116-
val firstFrameDate = SentryNanotimeDate(Date(1499), 0)
1115+
val firstFrameDate = SentryNanotimeDate(1499, 0)
11171116
fixture.options.dateProvider = SentryDateProvider { firstFrameDate }
1118-
setAppStartTime(SentryNanotimeDate(Date(1), 0))
1117+
setAppStartTime(SentryNanotimeDate(1, 0))
11191118

11201119
val activity = mock<Activity>()
11211120
sut.onActivityPreCreated(activity, fixture.bundle)
@@ -1168,8 +1167,8 @@ class ActivityLifecycleIntegrationTest {
11681167
it.isEnableStandaloneAppStartTracing = true
11691168
}
11701169
sut.register(fixture.scopes, fixture.options)
1171-
val appStartEndDate = SentryNanotimeDate(Date(499), 0)
1172-
setAppStartTime(SentryNanotimeDate(Date(1), 0), appStartEndDate)
1170+
val appStartEndDate = SentryNanotimeDate(499, 0)
1171+
setAppStartTime(SentryNanotimeDate(1, 0), appStartEndDate)
11731172

11741173
val activity = mock<Activity>()
11751174
sut.onActivityPreCreated(activity, fixture.bundle)
@@ -1230,9 +1229,9 @@ class ActivityLifecycleIntegrationTest {
12301229
AppStartMetrics.getInstance().appStartSentryTraceHeader =
12311230
SentryTraceHeader(storedTraceId, SpanId(), true).value
12321231
// headless start ended right before the activity opens
1233-
AppStartMetrics.getInstance().appStartEndTime = SentryNanotimeDate(Date(0), 0)
1232+
AppStartMetrics.getInstance().appStartEndTime = SentryNanotimeDate(0, 0)
12341233
sut.register(fixture.scopes, fixture.options)
1235-
setAppStartTime(date = SentryNanotimeDate(Date(1), 0))
1234+
setAppStartTime(date = SentryNanotimeDate(1, 0))
12361235

12371236
val activity = mock<Activity>()
12381237
sut.onActivityCreated(activity, fixture.bundle)
@@ -1254,9 +1253,9 @@ class ActivityLifecycleIntegrationTest {
12541253
AppStartMetrics.getInstance().appStartSentryTraceHeader =
12551254
SentryTraceHeader(storedTraceId, SpanId(), true).value
12561255
// headless start ended at epoch, but the activity opens more than a minute later
1257-
AppStartMetrics.getInstance().appStartEndTime = SentryNanotimeDate(Date(0), 0)
1256+
AppStartMetrics.getInstance().appStartEndTime = SentryNanotimeDate(0, 0)
12581257
sut.register(fixture.scopes, fixture.options)
1259-
setAppStartTime(date = SentryNanotimeDate(Date(TimeUnit.MINUTES.toMillis(2)), 0))
1258+
setAppStartTime(date = SentryNanotimeDate(TimeUnit.MINUTES.toMillis(2), 0))
12601259

12611260
val activity = mock<Activity>()
12621261
sut.onActivityCreated(activity, fixture.bundle)
@@ -1389,7 +1388,7 @@ class ActivityLifecycleIntegrationTest {
13891388

13901389
// usually done by SentryPerformanceProvider, if disabled it's done by
13911390
// SentryAndroid.init
1392-
val startDate = SentryNanotimeDate(Date(1), 0)
1391+
val startDate = SentryNanotimeDate(1, 0)
13931392
setAppStartTime(startDate)
13941393
AppStartMetrics.getInstance().appStartType = AppStartType.WARM
13951394

@@ -1415,7 +1414,7 @@ class ActivityLifecycleIntegrationTest {
14151414
sut.register(fixture.scopes, fixture.options)
14161415

14171416
// usually done by SentryPerformanceProvider
1418-
val startDate = SentryNanotimeDate(Date(1), 0)
1417+
val startDate = SentryNanotimeDate(1, 0)
14191418
setAppStartTime(startDate)
14201419
AppStartMetrics.getInstance().appStartType = AppStartType.WARM
14211420
AppStartMetrics.getInstance().sdkInitTimeSpan.setStoppedAt(1234)
@@ -1439,7 +1438,7 @@ class ActivityLifecycleIntegrationTest {
14391438
sut.register(fixture.scopes, fixture.options)
14401439

14411440
// usually done by SentryPerformanceProvider
1442-
val startDate = SentryNanotimeDate(Date(1), 0)
1441+
val startDate = SentryNanotimeDate(1, 0)
14431442
setAppStartTime(startDate)
14441443
AppStartMetrics.getInstance().appStartType = AppStartType.WARM
14451444

@@ -1474,7 +1473,7 @@ class ActivityLifecycleIntegrationTest {
14741473
sut.register(fixture.scopes, fixture.options)
14751474
sut.setFirstActivityCreated(true)
14761475

1477-
val date = SentryNanotimeDate(Date(1), 0)
1476+
val date = SentryNanotimeDate(1, 0)
14781477
setAppStartTime()
14791478

14801479
val activity = mock<Activity>()
@@ -1988,14 +1987,14 @@ class ActivityLifecycleIntegrationTest {
19881987
@Test
19891988
fun `When sentry is initialized mid activity lifecycle, last paused time should be used in favor of app start time`() {
19901989
val sut = fixture.getSut(importance = RunningAppProcessInfo.IMPORTANCE_FOREGROUND)
1991-
val now = SentryNanotimeDate(Date(1234), 456)
1990+
val now = SentryNanotimeDate(1234, 456)
19921991

19931992
fixture.options.tracesSampleRate = 1.0
19941993
fixture.options.dateProvider = SentryDateProvider { now }
19951994
sut.register(fixture.scopes, fixture.options)
19961995

19971996
// usually done by SentryPerformanceProvider
1998-
val startDate = SentryNanotimeDate(Date(5678), 910)
1997+
val startDate = SentryNanotimeDate(5678, 910)
19991998
setAppStartTime(startDate)
20001999
AppStartMetrics.getInstance().appStartType = AppStartType.COLD
20012000

@@ -2019,7 +2018,7 @@ class ActivityLifecycleIntegrationTest {
20192018
fixture.options.tracesSampleRate = 1.0
20202019
sut.register(fixture.scopes, fixture.options)
20212020

2022-
val date = SentryNanotimeDate(Date(1), 0)
2021+
val date = SentryNanotimeDate(1, 0)
20232022
setAppStartTime(date)
20242023

20252024
assertTrue(sut.activitySpanHelpers.isEmpty())
@@ -2036,8 +2035,8 @@ class ActivityLifecycleIntegrationTest {
20362035
fun `Creates activity lifecycle spans`() {
20372036
val sut = fixture.getSut()
20382037
fixture.options.tracesSampleRate = 1.0
2039-
val appStartDate = SentryNanotimeDate(Date(1), 0)
2040-
val startDate = SentryNanotimeDate(Date(2), 0)
2038+
val appStartDate = SentryNanotimeDate(1, 0)
2039+
val startDate = SentryNanotimeDate(2, 0)
20412040
val appStartMetrics = AppStartMetrics.getInstance()
20422041
val activity = mock<Activity>()
20432042
fixture.options.dateProvider = SentryDateProvider { startDate }
@@ -2076,7 +2075,7 @@ class ActivityLifecycleIntegrationTest {
20762075
fun `Creates activity lifecycle spans even when no app start span is available`() {
20772076
val sut = fixture.getSut()
20782077
fixture.options.tracesSampleRate = 1.0
2079-
val startDate = SentryNanotimeDate(Date(2), 0)
2078+
val startDate = SentryNanotimeDate(2, 0)
20802079
val appStartMetrics = AppStartMetrics.getInstance()
20812080
val activity = mock<Activity>()
20822081
fixture.options.dateProvider = SentryDateProvider { startDate }
@@ -2134,8 +2133,8 @@ class ActivityLifecycleIntegrationTest {
21342133
fun `Creates activity lifecycle spans on API lower than 29`() {
21352134
val sut = fixture.getSut(apiVersion = Build.VERSION_CODES.P)
21362135
fixture.options.tracesSampleRate = 1.0
2137-
val appStartDate = SentryNanotimeDate(Date(1), 0)
2138-
val startDate = SentryNanotimeDate(Date(2), 0)
2136+
val appStartDate = SentryNanotimeDate(1, 0)
2137+
val startDate = SentryNanotimeDate(2, 0)
21392138
val appStartMetrics = AppStartMetrics.getInstance()
21402139
val activity = mock<Activity>()
21412140
fixture.options.dateProvider = SentryDateProvider { startDate }
@@ -2187,8 +2186,8 @@ class ActivityLifecycleIntegrationTest {
21872186
fun `Does not add activity lifecycle spans when firstActivityCreated is true`() {
21882187
val sut = fixture.getSut()
21892188
fixture.options.tracesSampleRate = 1.0
2190-
val appStartDate = SentryNanotimeDate(Date(1), 0)
2191-
val startDate = SentryNanotimeDate(Date(2), 0)
2189+
val appStartDate = SentryNanotimeDate(1, 0)
2190+
val startDate = SentryNanotimeDate(2, 0)
21922191
val appStartMetrics = AppStartMetrics.getInstance()
21932192
val activity = mock<Activity>()
21942193
fixture.options.dateProvider = SentryDateProvider { startDate }
@@ -2209,7 +2208,7 @@ class ActivityLifecycleIntegrationTest {
22092208
fun `When firstActivityCreated is false and app start span has stopped, restart app start to current date`() {
22102209
val sut = fixture.getSut()
22112210
fixture.options.tracesSampleRate = 1.0
2212-
val appStartDate = SentryNanotimeDate(Date(1), 0)
2211+
val appStartDate = SentryNanotimeDate(1, 0)
22132212
val appStartMetrics = AppStartMetrics.getInstance()
22142213
val activity = mock<Activity>()
22152214
setAppStartTime(appStartDate)
@@ -2290,7 +2289,7 @@ class ActivityLifecycleIntegrationTest {
22902289
}
22912290

22922291
private fun setAppStartTime(
2293-
date: SentryDate = SentryNanotimeDate(Date(1), 0),
2292+
date: SentryDate = SentryNanotimeDate(1, 0),
22942293
stopDate: SentryDate? = null,
22952294
) {
22962295
// set by SentryPerformanceProvider so forcing it here

sentry-android-core/src/test/java/io/sentry/android/core/NetworkBreadcrumbsIntegrationTest.kt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import android.net.Network
55
import android.net.NetworkCapabilities
66
import android.os.Build
77
import io.sentry.Breadcrumb
8-
import io.sentry.DateUtils
98
import io.sentry.IScopes
109
import io.sentry.ISentryExecutorService
1110
import io.sentry.SentryDateProvider
@@ -54,8 +53,9 @@ class NetworkBreadcrumbsIntegrationTest {
5453
executorService = executor
5554
isEnableNetworkEventBreadcrumbs = enableNetworkEventBreadcrumbs
5655
dateProvider = SentryDateProvider {
57-
val nowNanos = TimeUnit.MILLISECONDS.toNanos(nowMs ?: System.currentTimeMillis())
58-
SentryNanotimeDate(DateUtils.nanosToDate(nowNanos), nowNanos)
56+
val nowMillis = nowMs ?: System.currentTimeMillis()
57+
val nowNanos = TimeUnit.MILLISECONDS.toNanos(nowMillis)
58+
SentryNanotimeDate(nowMillis, nowNanos)
5959
}
6060
}
6161
return NetworkBreadcrumbsIntegration(context, buildInfo)

sentry-android-core/src/test/java/io/sentry/android/core/SpanFrameMetricsCollectorTest.kt

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ import io.sentry.SentryNanotimeDate
88
import io.sentry.SpanContext
99
import io.sentry.android.core.internal.util.SentryFrameMetricsCollector
1010
import io.sentry.protocol.MeasurementValue
11-
import java.util.Date
1211
import java.util.UUID
1312
import java.util.concurrent.TimeUnit
1413
import kotlin.test.Test
@@ -50,11 +49,12 @@ class SpanFrameMetricsCollectorTest {
5049
val span = mock<ISpan>()
5150
val spanContext = SpanContext("op.fake")
5251
whenever(span.spanContext).thenReturn(spanContext)
53-
whenever(span.startDate).thenReturn(SentryNanotimeDate(Date(), startTimeStampNanos))
52+
whenever(span.startDate)
53+
.thenReturn(SentryNanotimeDate(System.currentTimeMillis(), startTimeStampNanos))
5454
whenever(span.finishDate)
5555
.thenReturn(
5656
if (endTimeStampNanos != null) {
57-
SentryNanotimeDate(Date(), endTimeStampNanos)
57+
SentryNanotimeDate(System.currentTimeMillis(), endTimeStampNanos)
5858
} else {
5959
null
6060
}
@@ -69,11 +69,12 @@ class SpanFrameMetricsCollectorTest {
6969
val span = mock<ITransaction>()
7070
val spanContext = SpanContext("op.fake")
7171
whenever(span.spanContext).thenReturn(spanContext)
72-
whenever(span.startDate).thenReturn(SentryNanotimeDate(Date(), startTimeStampNanos))
72+
whenever(span.startDate)
73+
.thenReturn(SentryNanotimeDate(System.currentTimeMillis(), startTimeStampNanos))
7374
whenever(span.finishDate)
7475
.thenReturn(
7576
if (endTimeStampNanos != null) {
76-
SentryNanotimeDate(Date(), endTimeStampNanos)
77+
SentryNanotimeDate(System.currentTimeMillis(), endTimeStampNanos)
7778
} else {
7879
null
7980
}
@@ -438,8 +439,8 @@ class SpanFrameMetricsCollectorTest {
438439
@Test
439440
fun `SentryNanoDate diff does nano precision`() {
440441
// having this in here, as SpanFrameMetricsCollector relies on this behavior
441-
val a = SentryNanotimeDate(Date(1234), 567)
442-
val b = SentryNanotimeDate(Date(1234), 0)
442+
val a = SentryNanotimeDate(1234, 567)
443+
val b = SentryNanotimeDate(1234, 0)
443444

444445
assertEquals(567, a.diff(b))
445446
}

0 commit comments

Comments
 (0)