Skip to content
Merged
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
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@

- Session Replay: Use main thread looper to schedule replay capture ([#4542](https://github.com/getsentry/sentry-java/pull/4542))
- Use single `LifecycleObserver` and multi-cast it to the integrations interested in lifecycle states ([#4567](https://github.com/getsentry/sentry-java/pull/4567))
- Add `sentry.origin` attribute to logs ([#4618](https://github.com/getsentry/sentry-java/pull/4618))
- This helps identify which integration captured a log event
- Prewarm `SentryExecutorService` for better performance at runtime ([#4606](https://github.com/getsentry/sentry-java/pull/4606))

### Fixes
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import io.sentry.Sentry;
import io.sentry.SentryLevel;
import io.sentry.SentryLogLevel;
import io.sentry.logger.SentryLogParameters;
import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
Expand Down Expand Up @@ -56,10 +57,13 @@ private static void addAsLog(
return;
}
final @Nullable String trMessage = tr != null ? tr.getMessage() : null;
final @NotNull SentryLogParameters params = new SentryLogParameters();
params.setOrigin("auto.log.logcat");

if (tr == null || trMessage == null) {
scopes.logger().log(level, msg);
scopes.logger().log(level, params, msg);
} else {
scopes.logger().log(level, msg != null ? (msg + "\n" + trMessage) : trMessage);
scopes.logger().log(level, params, msg != null ? (msg + "\n" + trMessage) : trMessage);
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ class SentryLogcatAdapterTest {
SentryLogcatAdapter.v(tag, "$commonMsg verbose")
fixture.breadcrumbs.first().assert(tag, "$commonMsg verbose", SentryLevel.DEBUG)
fixture.logs.first().assert("$commonMsg verbose", SentryLogLevel.TRACE)
assertEquals("auto.log.logcat", fixture.logs.first().attributes?.get("sentry.origin")?.value)
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import io.sentry.IScopes
import io.sentry.SentryEvent
import io.sentry.SentryLevel
import io.sentry.SentryLogLevel
import io.sentry.logger.SentryLogParameters
import io.sentry.protocol.Message
import timber.log.Timber

Expand Down Expand Up @@ -244,12 +245,15 @@ public class SentryTimberTree(
) {
// checks the log level
if (isLoggable(sentryLogLevel, minLogLevel)) {
val params = SentryLogParameters()
params.origin = "auto.log.timber"

val throwableMsg = throwable?.message
when {
msg != null && throwableMsg != null ->
scopes.logger().log(sentryLogLevel, "$msg\n$throwableMsg", *args)
msg != null -> scopes.logger().log(sentryLogLevel, msg, *args)
throwableMsg != null -> scopes.logger().log(sentryLogLevel, throwableMsg, *args)
scopes.logger().log(sentryLogLevel, params, "$msg\n$throwableMsg", *args)
msg != null -> scopes.logger().log(sentryLogLevel, params, msg, *args)
throwableMsg != null -> scopes.logger().log(sentryLogLevel, params, throwableMsg, *args)
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import io.sentry.Scopes
import io.sentry.SentryLevel
import io.sentry.SentryLogLevel
import io.sentry.logger.ILoggerApi
import io.sentry.logger.SentryLogParameters
import kotlin.test.BeforeTest
import kotlin.test.Test
import kotlin.test.assertEquals
Expand Down Expand Up @@ -248,21 +249,28 @@ class SentryTimberTreeTest {
val sut = fixture.getSut()
sut.e("test count: %d %d", 32, 5)

verify(fixture.logs).log(eq(SentryLogLevel.ERROR), eq("test count: %d %d"), eq(32), eq(5))
verify(fixture.logs)
.log(
eq(SentryLogLevel.ERROR),
check<SentryLogParameters> { assertEquals("auto.log.timber", it.origin) },
eq("test count: %d %d"),
eq(32),
eq(5),
)
}

@Test
fun `Tree adds a log if min level is equal`() {
val sut = fixture.getSut()
sut.i(Throwable("test"))
verify(fixture.logs).log(any(), any())
verify(fixture.logs).log(any(), any<SentryLogParameters>(), any<String>())
}

@Test
fun `Tree adds a log if min level is higher`() {
val sut = fixture.getSut()
sut.e(Throwable("test"))
verify(fixture.logs).log(any(), any<String>(), any())
verify(fixture.logs).log(any(), any<SentryLogParameters>(), any<String>(), any())
}

@Test
Expand All @@ -277,15 +285,25 @@ class SentryTimberTreeTest {
val sut = fixture.getSut()
sut.i("message")

verify(fixture.logs).log(eq(SentryLogLevel.INFO), eq("message"))
verify(fixture.logs)
.log(
eq(SentryLogLevel.INFO),
check<SentryLogParameters> { assertEquals("auto.log.timber", it.origin) },
eq("message"),
)
}

@Test
fun `Tree adds an error log`() {
val sut = fixture.getSut()
sut.e(Throwable("test"))

verify(fixture.logs).log(eq(SentryLogLevel.ERROR), eq("test"))
verify(fixture.logs)
.log(
eq(SentryLogLevel.ERROR),
check<SentryLogParameters> { assertEquals("auto.log.timber", it.origin) },
eq("test"),
)
}

@Test
Expand All @@ -300,14 +318,24 @@ class SentryTimberTreeTest {
val sut = fixture.getSut()
sut.e(Throwable("throwable message"))

verify(fixture.logs).log(eq(SentryLogLevel.ERROR), eq("throwable message"))
verify(fixture.logs)
.log(
eq(SentryLogLevel.ERROR),
check<SentryLogParameters> { assertEquals("auto.log.timber", it.origin) },
eq("throwable message"),
)
}

@Test
fun `Tree logs throwable and message`() {
val sut = fixture.getSut()
sut.e(Throwable("throwable message"), "My message")

verify(fixture.logs).log(eq(SentryLogLevel.ERROR), eq("My message\nthrowable message"))
verify(fixture.logs)
.log(
eq(SentryLogLevel.ERROR),
check<SentryLogParameters> { assertEquals("auto.log.timber", it.origin) },
eq("My message\nthrowable message"),
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,7 @@ protected void captureLog(@NotNull LogRecord loggingEvent) {

final @NotNull String formattedMessage = maybeFormatted(arguments, message);
final @NotNull SentryLogParameters params = SentryLogParameters.create(attributes);
params.setOrigin("auto.log.jul");

Sentry.logger().log(sentryLevel, params, formattedMessage, arguments);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -414,7 +414,12 @@ class SentryHandlerTest {
Sentry.flush(1000)

verify(fixture.transport)
.send(checkLogs { event -> assertEquals(SentryLogLevel.TRACE, event.items.first().level) })
.send(
checkLogs { event ->
assertEquals(SentryLogLevel.TRACE, event.items.first().level)
assertEquals("auto.log.jul", event.items.first().attributes?.get("sentry.origin")?.value)
}
)
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -228,6 +228,7 @@ protected void captureLog(@NotNull LogEvent loggingEvent) {

final @NotNull String formattedMessage = loggingEvent.getMessage().getFormattedMessage();
final @NotNull SentryLogParameters params = SentryLogParameters.create(attributes);
params.setOrigin("auto.log.log4j2");

Sentry.logger().log(sentryLevel, params, formattedMessage, arguments);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -251,7 +251,15 @@ class SentryAppenderTest {
Sentry.flush(1000)

verify(fixture.transport)
.send(checkLogs { event -> assertEquals(SentryLogLevel.TRACE, event.items.first().level) })
.send(
checkLogs { event ->
assertEquals(SentryLogLevel.TRACE, event.items.first().level)
assertEquals(
"auto.log.log4j2",
event.items.first().attributes?.get("sentry.origin")?.value,
)
}
)
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -193,6 +193,7 @@ protected void captureLog(@NotNull ILoggingEvent loggingEvent) {

final @NotNull String formattedMessage = formatted(loggingEvent);
final @NotNull SentryLogParameters params = SentryLogParameters.create(attributes);
params.setOrigin("auto.log.logback");

Sentry.logger().log(sentryLevel, params, formattedMessage, arguments);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -382,6 +382,7 @@ class SentryAppenderTest {
val attributes = log.attributes!!
assertEquals("Testing {} level", attributes["sentry.message.template"]?.value)
assertEquals("TRACE", attributes["sentry.message.parameter.0"]?.value)
assertEquals("auto.log.logback", attributes["sentry.origin"]?.value)
}
)
}
Expand Down
2 changes: 2 additions & 0 deletions sentry/api/sentry.api
Original file line number Diff line number Diff line change
Expand Up @@ -4871,8 +4871,10 @@ public final class io/sentry/logger/SentryLogParameters {
public static fun create (Lio/sentry/SentryAttributes;)Lio/sentry/logger/SentryLogParameters;
public static fun create (Lio/sentry/SentryDate;Lio/sentry/SentryAttributes;)Lio/sentry/logger/SentryLogParameters;
public fun getAttributes ()Lio/sentry/SentryAttributes;
public fun getOrigin ()Ljava/lang/String;
public fun getTimestamp ()Lio/sentry/SentryDate;
public fun setAttributes (Lio/sentry/SentryAttributes;)V
public fun setOrigin (Ljava/lang/String;)V
public fun setTimestamp (Lio/sentry/SentryDate;)V
}

Expand Down
9 changes: 7 additions & 2 deletions sentry/src/main/java/io/sentry/logger/LoggerApi.java
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ private void captureLog(
span == null ? propagationContext.getSpanId() : span.getSpanContext().getSpanId();
final SentryLogEvent logEvent =
new SentryLogEvent(traceId, timestampToUse, messageToUse, level);
logEvent.setAttributes(createAttributes(params.getAttributes(), message, spanId, args));
logEvent.setAttributes(createAttributes(params, message, spanId, args));
logEvent.setSeverityNumber(level.getSeverityNumber());

scopes.getClient().captureLog(logEvent, combinedScope);
Expand All @@ -160,11 +160,16 @@ private void captureLog(
}

private @NotNull HashMap<String, SentryLogEventAttributeValue> createAttributes(
final @Nullable SentryAttributes incomingAttributes,
final @NotNull SentryLogParameters params,
final @NotNull String message,
final @NotNull SpanId spanId,
final @Nullable Object... args) {
final @NotNull HashMap<String, SentryLogEventAttributeValue> attributes = new HashMap<>();
attributes.put(
"sentry.origin",
new SentryLogEventAttributeValue(SentryAttributeType.STRING, params.getOrigin()));

final @Nullable SentryAttributes incomingAttributes = params.getAttributes();

if (incomingAttributes != null) {
for (SentryAttribute attribute : incomingAttributes.getAttributes().values()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ public final class SentryLogParameters {

private @Nullable SentryDate timestamp;
private @Nullable SentryAttributes attributes;
private @NotNull String origin = "manual";

public @Nullable SentryDate getTimestamp() {
return timestamp;
Expand All @@ -26,6 +27,14 @@ public void setAttributes(final @Nullable SentryAttributes attributes) {
this.attributes = attributes;
}

public @NotNull String getOrigin() {
return origin;
}

public void setOrigin(final @NotNull String origin) {
this.origin = origin;
}

public static @NotNull SentryLogParameters create(
final @Nullable SentryDate timestamp, final @Nullable SentryAttributes attributes) {
final @NotNull SentryLogParameters params = new SentryLogParameters();
Expand Down
Loading