Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
# Changelog

## Unreleased

### Features

- Android: Files attached to the scope will now be synced to native ([#5211](https://github.com/getsentry/sentry-java/pull/5211))

## 8.36.0

### Features
Expand Down
2 changes: 1 addition & 1 deletion gradle/libs.versions.toml
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,7 @@ quartz = { module = "org.quartz-scheduler:quartz", version = "2.3.0" }
reactor-core = { module = "io.projectreactor:reactor-core", version = "3.5.3" }
retrofit = { module = "com.squareup.retrofit2:retrofit", version.ref = "retrofit" }
retrofit-gson = { module = "com.squareup.retrofit2:converter-gson", version.ref = "retrofit" }
sentry-native-ndk = { module = "io.sentry:sentry-native-ndk", version = "0.13.2" }
sentry-native-ndk = { module = "io.sentry:sentry-native-ndk", version = "0.13.3" }
servlet-api = { module = "javax.servlet:javax.servlet-api", version = "3.1.0" }
servlet-jakarta-api = { module = "jakarta.servlet:jakarta.servlet-api", version = "6.1.0" }
slf4j-api = { module = "org.slf4j:slf4j-api", version.ref = "slf4j" }
Expand Down
2 changes: 2 additions & 0 deletions sentry-android-ndk/api/sentry-android-ndk.api
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@ public final class io/sentry/android/ndk/DebugImagesLoader : io/sentry/android/c

public final class io/sentry/android/ndk/NdkScopeObserver : io/sentry/ScopeObserverAdapter {
public fun <init> (Lio/sentry/SentryOptions;)V
public fun addAttachment (Lio/sentry/Attachment;)V
public fun addBreadcrumb (Lio/sentry/Breadcrumb;)V
public fun clearAttachments ()V
public fun removeExtra (Ljava/lang/String;)V
public fun removeTag (Ljava/lang/String;)V
public fun setExtra (Ljava/lang/String;Ljava/lang/String;)V
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.sentry.android.ndk;

import io.sentry.Attachment;
import io.sentry.Breadcrumb;
import io.sentry.DateUtils;
import io.sentry.IScope;
Expand Down Expand Up @@ -145,4 +146,41 @@ public void setTrace(@Nullable SpanContext spanContext, @NotNull IScope scope) {
options.getLogger().log(SentryLevel.ERROR, e, "Scope sync setTrace failed.");
}
}

@Override
public void addAttachment(final @NotNull Attachment attachment) {
final String pathname = attachment.getPathname();
if (pathname != null) {
try {
options.getExecutorService().submit(() -> nativeScope.addAttachment(pathname));
} catch (Throwable e) {
options.getLogger().log(SentryLevel.ERROR, e, "Scope sync addAttachment has an error.");
}
return;
}

final byte[] bytes = attachment.getBytes();
if (bytes != null) {
final String filename = attachment.getFilename();
try {
options.getExecutorService().submit(() -> nativeScope.addAttachmentBytes(bytes, filename));
} catch (Throwable e) {
options.getLogger().log(SentryLevel.ERROR, e, "Scope sync addAttachment has an error.");
}
return;
}

options
.getLogger()
.log(SentryLevel.DEBUG, "Scope sync addAttachment skips attachment without path or bytes.");
}

@Override
public void clearAttachments() {
try {
options.getExecutorService().submit(() -> nativeScope.clearAttachments());
} catch (Throwable e) {
options.getLogger().log(SentryLevel.ERROR, e, "Scope sync clearAttachments has an error.");
}
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.sentry.android.ndk

import io.sentry.Attachment
import io.sentry.Breadcrumb
import io.sentry.DateUtils
import io.sentry.JsonSerializer
Expand Down Expand Up @@ -153,4 +154,34 @@ class NdkScopeObserverTest {
verify(fixture.nativeScope)
.addBreadcrumb(anyOrNull(), anyOrNull(), anyOrNull(), anyOrNull(), anyOrNull(), anyOrNull())
}

@Test
fun `add file-path attachment syncs to native scope`() {
val sut = fixture.getSut()

val attachment = Attachment("/data/data/com.example/files/log.txt")
sut.addAttachment(attachment)

verify(fixture.nativeScope).addAttachment("/data/data/com.example/files/log.txt")
}

@Test
fun `add byte attachment syncs bytes to native scope`() {
val sut = fixture.getSut()

val bytes = byteArrayOf(1, 2, 3)
val attachment = Attachment(bytes, "data.bin")
sut.addAttachment(attachment)

verify(fixture.nativeScope).addAttachmentBytes(bytes, "data.bin")
}

@Test
fun `clear attachments forwards call to native scope`() {
val sut = fixture.getSut()

sut.clearAttachments()

verify(fixture.nativeScope).clearAttachments()
}
}
4 changes: 4 additions & 0 deletions sentry/api/sentry.api
Original file line number Diff line number Diff line change
Expand Up @@ -943,7 +943,9 @@ public abstract interface class io/sentry/IScope {
}

public abstract interface class io/sentry/IScopeObserver {
public abstract fun addAttachment (Lio/sentry/Attachment;)V
public abstract fun addBreadcrumb (Lio/sentry/Breadcrumb;)V
public abstract fun clearAttachments ()V
public abstract fun removeExtra (Ljava/lang/String;)V
public abstract fun removeTag (Ljava/lang/String;)V
public abstract fun setBreadcrumbs (Ljava/util/Collection;)V
Expand Down Expand Up @@ -2446,7 +2448,9 @@ public abstract interface class io/sentry/ScopeCallback {

public abstract class io/sentry/ScopeObserverAdapter : io/sentry/IScopeObserver {
public fun <init> ()V
public fun addAttachment (Lio/sentry/Attachment;)V
public fun addBreadcrumb (Lio/sentry/Breadcrumb;)V
public fun clearAttachments ()V
public fun removeExtra (Ljava/lang/String;)V
public fun removeTag (Ljava/lang/String;)V
public fun setBreadcrumbs (Ljava/util/Collection;)V
Expand Down
4 changes: 4 additions & 0 deletions sentry/src/main/java/io/sentry/IScopeObserver.java
Original file line number Diff line number Diff line change
Expand Up @@ -45,4 +45,8 @@ public interface IScopeObserver {
void setTrace(@Nullable SpanContext spanContext, @NotNull IScope scope);

void setReplayId(@NotNull SentryId replayId);

void addAttachment(@NotNull Attachment attachment);

void clearAttachments();
}
8 changes: 8 additions & 0 deletions sentry/src/main/java/io/sentry/Scope.java
Original file line number Diff line number Diff line change
Expand Up @@ -924,12 +924,20 @@ public List<Attachment> getAttachments() {
@Override
public void addAttachment(final @NotNull Attachment attachment) {
attachments.add(attachment);

for (final IScopeObserver observer : options.getScopeObservers()) {
observer.addAttachment(attachment);
}
}

/** Clear all attachments. */
@Override
public void clearAttachments() {
attachments.clear();

for (final IScopeObserver observer : options.getScopeObservers()) {
observer.clearAttachments();
}
}

/**
Expand Down
6 changes: 6 additions & 0 deletions sentry/src/main/java/io/sentry/ScopeObserverAdapter.java
Original file line number Diff line number Diff line change
Expand Up @@ -57,4 +57,10 @@ public void setTrace(@Nullable SpanContext spanContext, @NotNull IScope scope) {

@Override
public void setReplayId(@NotNull SentryId replayId) {}

@Override
public void addAttachment(@NotNull Attachment attachment) {}

@Override
public void clearAttachments() {}
}
Loading