Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
0627186
Add Log feature to Java SDK
adinauer May 6, 2025
27a24ec
Rate limit for log items
adinauer May 6, 2025
0c75319
Add options for logs
adinauer May 7, 2025
bc8caf7
Add batch processor for logs
adinauer May 8, 2025
38c3dcd
Use a separate ExecutorService for log batching
adinauer May 8, 2025
c639bfc
Reduce locking when log event is created
adinauer May 8, 2025
217f7c7
Add system tests for Logs
adinauer May 12, 2025
fef4582
Separate enum for SentryLogLevel
adinauer May 12, 2025
ac2bce7
Remove logsSampleRate option
adinauer May 12, 2025
50078d0
Move logs options out of experimental namespace
adinauer May 12, 2025
d0fef91
Add severity_number to SentryLogItem
adinauer May 12, 2025
60dc14b
Logs review feedback
adinauer May 12, 2025
69d6a81
mark captureBatchedLogEvents internal
adinauer May 13, 2025
88f4c96
remove hint for logs
adinauer May 13, 2025
44211bd
Attach server.address to logs
adinauer May 13, 2025
e7c9212
Allow null for log event attribute value
adinauer May 13, 2025
3263bc1
Merge branch 'feat/logs-review-feedback' into feat/logs-server-address
adinauer May 13, 2025
5ba33fd
Merge branch 'main' into feat/logs-e2e-tests
adinauer May 13, 2025
a7afc9d
Merge branch 'feat/logs-e2e-tests' into feat/separate-log-level-enum
adinauer May 13, 2025
164f210
Merge branch 'main' into feat/separate-log-level-enum
adinauer May 13, 2025
893b67c
Merge branch 'feat/separate-log-level-enum' into feat/remove-logs-sam…
adinauer May 13, 2025
80e5bb9
Merge branch 'main' into feat/remove-logs-sample-rate-option
adinauer May 13, 2025
c1ca9be
Merge branch 'feat/remove-logs-sample-rate-option' into feat/logs-not…
adinauer May 13, 2025
808b4e6
Merge branch 'main' into feat/logs-not-experimental
adinauer May 13, 2025
e167f1b
Merge branch 'feat/logs-not-experimental' into feat/logs-severity-number
adinauer May 13, 2025
c07e44c
Merge branch 'main' into feat/logs-severity-number
adinauer May 13, 2025
888ab48
Merge branch 'feat/logs-severity-number' into feat/logs-review-feedback
adinauer May 13, 2025
7894f55
Merge branch 'main' into feat/logs-review-feedback
adinauer May 13, 2025
ddbca2b
Merge branch 'feat/logs-review-feedback' into feat/logs-server-address
adinauer May 13, 2025
17ad65f
Merge branch 'main' into feat/logs-server-address
adinauer May 13, 2025
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
5 changes: 5 additions & 0 deletions sentry/api/sentry.api
Original file line number Diff line number Diff line change
Expand Up @@ -589,6 +589,11 @@ public final class io/sentry/Hint {
public static fun withAttachments (Ljava/util/List;)Lio/sentry/Hint;
}

public final class io/sentry/HostnameCache {
public fun getHostname ()Ljava/lang/String;
public static fun getInstance ()Lio/sentry/HostnameCache;
}

public final class io/sentry/HttpStatusCodeRange {
public static final field DEFAULT_MAX I
public static final field DEFAULT_MIN I
Expand Down
20 changes: 15 additions & 5 deletions sentry/src/main/java/io/sentry/HostnameCache.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.sentry;

import io.sentry.util.AutoClosableReentrantLock;
import io.sentry.util.Objects;
import java.net.InetAddress;
import java.util.concurrent.Callable;
Expand All @@ -11,6 +12,7 @@
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
import java.util.concurrent.atomic.AtomicBoolean;
import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

Expand All @@ -25,13 +27,16 @@
* <p>HostnameCache is a singleton and its instance should be obtained through {@link
* HostnameCache#getInstance()}.
*/
final class HostnameCache {
@ApiStatus.Internal
public final class HostnameCache {
private static final long HOSTNAME_CACHE_DURATION = TimeUnit.HOURS.toMillis(5);

/** Time before the get hostname operation times out (in ms). */
private static final long GET_HOSTNAME_TIMEOUT = TimeUnit.SECONDS.toMillis(1);

@Nullable private static HostnameCache INSTANCE;
private static volatile @Nullable HostnameCache INSTANCE;
private static final @NotNull AutoClosableReentrantLock staticLock =
new AutoClosableReentrantLock();

/** Time for which the cache is kept. */
private final long cacheDuration;
Expand All @@ -47,10 +52,15 @@ final class HostnameCache {
private final @NotNull ExecutorService executorService =
Executors.newSingleThreadExecutor(new HostnameCacheThreadFactory());

static @NotNull HostnameCache getInstance() {
public static @NotNull HostnameCache getInstance() {
if (INSTANCE == null) {
INSTANCE = new HostnameCache();
try (final @NotNull ISentryLifecycleToken ignored = staticLock.acquire()) {
if (INSTANCE == null) {
INSTANCE = new HostnameCache();
}
}
}

return INSTANCE;
}

Expand Down Expand Up @@ -93,7 +103,7 @@ boolean isClosed() {
* @return the hostname of the current machine.
*/
@Nullable
String getHostname() {
public String getHostname() {
if (expirationTimestamp < System.currentTimeMillis()
&& updateRunning.compareAndSet(false, true)) {
updateCache();
Expand Down
9 changes: 1 addition & 8 deletions sentry/src/main/java/io/sentry/MainEventProcessor.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
import io.sentry.protocol.SentryException;
import io.sentry.protocol.SentryTransaction;
import io.sentry.protocol.User;
import io.sentry.util.AutoClosableReentrantLock;
import io.sentry.util.HintUtils;
import io.sentry.util.Objects;
import java.io.Closeable;
Expand All @@ -28,8 +27,6 @@ public final class MainEventProcessor implements EventProcessor, Closeable {
private final @NotNull SentryThreadFactory sentryThreadFactory;
private final @NotNull SentryExceptionFactory sentryExceptionFactory;
private volatile @Nullable HostnameCache hostnameCache = null;
private final @NotNull AutoClosableReentrantLock hostnameCacheLock =
new AutoClosableReentrantLock();

public MainEventProcessor(final @NotNull SentryOptions options) {
this.options = Objects.requireNonNull(options, "The SentryOptions is required.");
Expand Down Expand Up @@ -183,11 +180,7 @@ private void setServerName(final @NotNull SentryBaseEvent event) {

private void ensureHostnameCache() {
if (hostnameCache == null) {
try (final @NotNull ISentryLifecycleToken ignored = hostnameCacheLock.acquire()) {
if (hostnameCache == null) {
hostnameCache = HostnameCache.getInstance();
}
}
hostnameCache = HostnameCache.getInstance();
}
}

Expand Down
22 changes: 22 additions & 0 deletions sentry/src/main/java/io/sentry/logger/LoggerApi.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package io.sentry.logger;

import io.sentry.HostnameCache;
import io.sentry.IScope;
import io.sentry.ISpan;
import io.sentry.PropagationContext;
Expand All @@ -13,6 +14,7 @@
import io.sentry.SpanId;
import io.sentry.protocol.SdkVersion;
import io.sentry.protocol.SentryId;
import io.sentry.util.Platform;
import io.sentry.util.TracingUtils;
import java.util.HashMap;
import org.jetbrains.annotations.ApiStatus;
Expand Down Expand Up @@ -163,9 +165,29 @@ private void captureLog(

attributes.put(
"sentry.trace.parent_span_id", new SentryLogEventAttributeValue("string", spanId));

if (Platform.isJvm()) {
setServerName(attributes);
}

return attributes;
}

private void setServerName(
final @NotNull HashMap<String, SentryLogEventAttributeValue> attributes) {
final @NotNull SentryOptions options = scopes.getOptions();
final @Nullable String optionsServerName = options.getServerName();
if (optionsServerName != null) {
attributes.put(
"server.address", new SentryLogEventAttributeValue("string", optionsServerName));
} else if (options.isAttachServerName()) {
final @Nullable String hostname = HostnameCache.getInstance().getHostname();
if (hostname != null) {
attributes.put("server.address", new SentryLogEventAttributeValue("string", hostname));
}
}
}

private @NotNull String getType(final @Nullable Object arg) {
if (arg instanceof Boolean) {
return "boolean";
Expand Down
Loading