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
8 changes: 7 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,16 @@

## Unreleased

### Features

- Metrics are no longer experimental ([#2592](https://github.com/getsentry/sentry-unity/pull/2592))

## 4.1.2

### Fixes

- `CaptureFeedback` now returns a `SentryId` and exposes a `CaptureFeedbackResult` out parameter to indicate whether feedback was captured successfully ([#2589](https://github.com/getsentry/sentry-unity/pull/2579))
- When exporting a NSP ROM File for Switch the SKD now correctly uploads the debug symbols ([#2580](https://github.com/getsentry/sentry-unity/pull/2580))
- When exporting a NSP ROM File for Switch the SKD now correctly uploads the debug symbols ([#2580](https://github.com/getsentry/sentry-unity/pull/2580))
- The SDK now also uses `.sentry-native` as a subdirectory for native support on desktop platforms. It now also falls back to `Application.persistentDataPath` instead of the current working directory. Note: `crashedLastRun` may report `false` for the first time after upgrading. ([#2547](https://github.com/getsentry/sentry-unity/pull/2547))
- The currently experimental Metrics are now opt-in by default ([#2546](https://github.com/getsentry/sentry-unity/pull/2546))
- When targeting Android, the SDK now syncs `AppStartTime` and `AppBuildType` to the native layer ([#2557](https://github.com/getsentry/sentry-unity/pull/2557))
Expand Down
23 changes: 17 additions & 6 deletions Directory.Build.targets
Original file line number Diff line number Diff line change
Expand Up @@ -221,6 +221,12 @@ Expected to exist:

<Message Importance="High" Text="Building Sentry Android SDK." />

<!-- Clean stale jars from previous builds to avoid glob ambiguity -->
<ItemGroup>
<StaleJarArtifacts Include="$(SentryAndroidRoot)sentry/build/libs/sentry*.jar" />
</ItemGroup>
<Delete Files="@(StaleJarArtifacts)" />

<Exec WorkingDirectory="$(SentryAndroidRoot)" Command="./gradlew -PsentryAndroidSdkName=sentry.native.android.unity :sentry-android-core:assembleRelease :sentry-android-ndk:assembleRelease :sentry:jar --no-daemon --stacktrace --warning-mode none" />

<ItemGroup>
Expand All @@ -246,28 +252,33 @@ Expected to exist:
<PropertyGroup>
<PropertiesContent>$([System.IO.File]::ReadAllText("$(RepoRoot)modules/sentry-java/gradle/libs.versions.toml"))</PropertiesContent>
<NativeVersion>$([System.Text.RegularExpressions.Regex]::Match($(PropertiesContent), 'sentry-native-ndk\s*=\s*\{[^}]*version\s*=\s*"([^"]+)"').Groups[1].Value)</NativeVersion>
<LocalNativeNdkAar>$(RepoRoot)modules/sentry-native/ndk/lib/build/outputs/aar/sentry-native-ndk-release.aar</LocalNativeNdkAar>
</PropertyGroup>

<!-- Use local build output if available (e.g. dev versions), otherwise download from GitHub releases -->
<Message Condition="Exists('$(LocalNativeNdkAar)')" Importance="High" Text="Using locally built sentry-native-ndk AAR." />
<Copy Condition="Exists('$(LocalNativeNdkAar)')" SourceFiles="$(LocalNativeNdkAar)" DestinationFiles="$(SentryAndroidArtifactsDestination)sentry-native-ndk-release.aar" />

<!-- Clean cache if version does not exist to get rid of old versions -->
<RemoveDir
Condition="!Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip')"
Condition="!Exists('$(LocalNativeNdkAar)') And !Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip')"
Directories="$(SentryNativeNdkCache)" />

<!-- Create cache directory -->
<MakeDir Condition="!Exists('$(SentryNativeNdkCache)')" Directories="$(SentryNativeNdkCache)" />
<MakeDir Condition="!Exists('$(LocalNativeNdkAar)') And !Exists('$(SentryNativeNdkCache)')" Directories="$(SentryNativeNdkCache)" />

<Message Importance="High" Text="Downloading sentry-native-ndk version '$(NativeVersion)'." />
<Message Condition="!Exists('$(LocalNativeNdkAar)')" Importance="High" Text="Downloading sentry-native-ndk version '$(NativeVersion)'." />

<!-- Download prebuilt sentry-native-ndk -->
<Exec
Condition="!Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip')"
Condition="!Exists('$(LocalNativeNdkAar)') And !Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip')"
Command="curl -L https://github.com/getsentry/sentry-native/releases/download/$(NativeVersion)/sentry-native-ndk-$(NativeVersion).zip -o &quot;$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip&quot;" />

<Exec
Condition="!Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion)')"
Condition="!Exists('$(LocalNativeNdkAar)') And !Exists('$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion)')"
Command="pwsh -Command &quot;Expand-Archive -Path '$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion).zip' -DestinationPath '$(SentryNativeNdkCache)' -Force&quot;" />

<Copy SourceFiles="$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion)/sentry-native-ndk-release.aar" DestinationFiles="$(SentryAndroidArtifactsDestination)sentry-native-ndk-release.aar" />
<Copy Condition="!Exists('$(LocalNativeNdkAar)')" SourceFiles="$(SentryNativeNdkCache)sentry-native-ndk-$(NativeVersion)/sentry-native-ndk-release.aar" DestinationFiles="$(SentryAndroidArtifactsDestination)sentry-native-ndk-release.aar" />

<Error Condition="!Exists('$(SentryAndroidArtifactsDestination)')" Text="Failed to build the Android SDK." />
</Target>
Expand Down
9 changes: 9 additions & 0 deletions src/Sentry.Unity.Android/AndroidJavaScopeObserver.cs
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,13 @@ public override void UnsetUserImpl() =>

public override void SetTraceImpl(SentryId traceId, SpanId spanId) =>
_sentryJava.SetTrace(traceId, spanId);

public override void AddFileAttachmentImpl(string filePath, string fileName, string? contentType) =>
_sentryJava.AddAttachment(filePath, fileName, contentType);

public override void AddByteAttachmentImpl(byte[] data, string fileName, string? contentType) =>
_sentryJava.AddAttachmentBytes(data, fileName, contentType);

public override void ClearAttachmentsImpl() =>
_sentryJava.ClearAttachments();
}
41 changes: 41 additions & 0 deletions src/Sentry.Unity.Android/SentryJava.cs
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,9 @@ public void WriteScope(
public void SetUser(SentryUser user);
public void UnsetUser();
public void SetTrace(SentryId traceId, SpanId spanId);
void AddAttachment(string path, string fileName, string? contentType);
void AddAttachmentBytes(byte[] data, string fileName, string? contentType);
void ClearAttachments();
}

/// <summary>
Expand Down Expand Up @@ -361,6 +364,44 @@ public void SetTrace(SentryId traceId, SpanId spanId)
});
}

public void AddAttachment(string path, string fileName, string? contentType)
{
RunJniSafe(() =>
{
using var attachment = contentType is not null
? new AndroidJavaObject("io.sentry.Attachment", path, fileName, contentType)
: new AndroidJavaObject("io.sentry.Attachment", path, fileName);

using var sentry = GetSentryJava();
sentry.CallStatic("configureScope", new ScopeCallback(scope =>
scope.Call("addAttachment", attachment)));
});
}

public void AddAttachmentBytes(byte[] data, string fileName, string? contentType)
{
RunJniSafe(() =>
{
using var attachment = contentType is not null
? new AndroidJavaObject("io.sentry.Attachment", data, fileName, contentType)
: new AndroidJavaObject("io.sentry.Attachment", data, fileName);

using var sentry = GetSentryJava();
sentry.CallStatic("configureScope", new ScopeCallback(scope =>
scope.Call("addAttachment", attachment)));
});
}

public void ClearAttachments()
{
RunJniSafe(() =>
{
using var sentry = GetSentryJava();
sentry.CallStatic("configureScope", new ScopeCallback(scope =>
scope.Call("clearAttachments")));
});
}

// https://github.com/getsentry/sentry-java/blob/db4dfc92f202b1cefc48d019fdabe24d487db923/sentry/src/main/java/io/sentry/SentryLevel.java#L4-L9
internal static string GetLevelString(SentryLevel level) => level switch
{
Expand Down
9 changes: 9 additions & 0 deletions src/Sentry.Unity.Native/CFunctions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,15 @@ internal static void SetValueIfNotNull(sentry_value_t obj, string key, long? val
[DllImport(SentryLib)]
internal static extern void sentry_set_trace(string traceId, string parentSpanId);

[DllImport(SentryLib)]
internal static extern IntPtr sentry_attach_file(string path);

[DllImport(SentryLib)]
internal static extern IntPtr sentry_attach_bytes(byte[] buf, UIntPtr buf_len, string filename);

[DllImport(SentryLib)]
internal static extern void sentry_clear_attachments();

internal static readonly Lazy<IEnumerable<DebugImage>> DebugImages = new(LoadDebugImages);

private static IEnumerable<DebugImage> LoadDebugImages()
Expand Down
9 changes: 9 additions & 0 deletions src/Sentry.Unity.Native/NativeScopeObserver.cs
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,15 @@ public override void SetUserImpl(SentryUser user)
public override void SetTraceImpl(SentryId traceId, SpanId spanId) =>
C.sentry_set_trace(traceId.ToString(), spanId.ToString());

public override void AddFileAttachmentImpl(string filePath, string fileName, string? contentType) =>
C.sentry_attach_file(filePath);

public override void AddByteAttachmentImpl(byte[] data, string fileName, string? contentType) =>
C.sentry_attach_bytes(data, (UIntPtr)data.Length, fileName);

public override void ClearAttachmentsImpl() =>
C.sentry_clear_attachments();

private static string GetTimestamp(DateTimeOffset timestamp) =>
// "o": Using ISO 8601 to make sure the timestamp makes it to the bridge correctly.
// https://docs.microsoft.com/en-gb/dotnet/standard/base-types/standard-date-and-time-format-strings#Roundtrip
Expand Down
15 changes: 15 additions & 0 deletions src/Sentry.Unity.iOS/NativeScopeObserver.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,21 @@ public override void SetUserImpl(SentryUser user) =>
public override void SetTraceImpl(SentryId traceId, SpanId spanId) =>
SentryCocoaBridgeProxy.SetTrace(traceId.ToString(), spanId.ToString());

public override void AddFileAttachmentImpl(string filePath, string fileName, string? contentType)
{
// iOS/macOS attachment sync to sentry-cocoa is not yet supported.
}

public override void AddByteAttachmentImpl(byte[] data, string fileName, string? contentType)
{
// iOS/macOS attachment sync to sentry-cocoa is not yet supported.
}

public override void ClearAttachmentsImpl()
{
// iOS/macOS attachment sync to sentry-cocoa is not yet supported.
}

internal static string GetTimestamp(DateTimeOffset timestamp) =>
// "o": Using ISO 8601 to make sure the timestamp makes it to the bridge correctly.
// https://docs.microsoft.com/en-gb/dotnet/standard/base-types/standard-date-and-time-format-strings#Roundtrip
Expand Down
30 changes: 30 additions & 0 deletions src/Sentry.Unity/ScopeObserver.cs
Original file line number Diff line number Diff line change
Expand Up @@ -86,4 +86,34 @@ public void SetTrace(SentryId traceId, SpanId spanId)
}

public abstract void SetTraceImpl(SentryId traceId, SpanId spanId);

public void AddAttachment(SentryAttachment attachment)
{
if (attachment.Content is FileAttachmentContent fileContent)
{
_options.LogDebug("{0} Scope Sync - Adding file attachment \"{1}\"", _name, fileContent.FilePath);
AddFileAttachmentImpl(fileContent.FilePath, attachment.FileName, attachment.ContentType);
}
else if (attachment.Content is ByteAttachmentContent byteContent)
{
_options.LogDebug("{0} Scope Sync - Adding byte attachment \"{1}\" ({2} bytes)", _name, attachment.FileName, byteContent.Bytes.Length);
AddByteAttachmentImpl(byteContent.Bytes, attachment.FileName, attachment.ContentType);
}
else
{
_options.LogDebug("{0} Scope Sync - Skipping attachment \"{1}\" (unsupported content type for native sync)", _name, attachment.FileName);
}
}

public abstract void AddFileAttachmentImpl(string filePath, string fileName, string? contentType);

public abstract void AddByteAttachmentImpl(byte[] data, string fileName, string? contentType);

public void ClearAttachments()
{
_options.LogDebug("{0} Scope Sync - Clearing attachments", _name);
ClearAttachmentsImpl();
}

public abstract void ClearAttachmentsImpl();
}
6 changes: 6 additions & 0 deletions test/Sentry.Unity.Android.Tests/TestSentryJava.cs
Original file line number Diff line number Diff line change
Expand Up @@ -54,4 +54,10 @@ public void SetUser(SentryUser user) { }
public void UnsetUser() { }

public void SetTrace(SentryId traceId, SpanId spanId) { }

public void AddAttachment(string path, string fileName, string? contentType) { }

public void AddAttachmentBytes(byte[] data, string fileName, string? contentType) { }

public void ClearAttachments() { }
}
Loading