diff --git a/CHANGELOG.md b/CHANGELOG.md index 41e651319..fe2eab549 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -25,6 +25,9 @@ - Bump Native SDK from v0.14.0 to v0.14.2 ([#2685](https://github.com/getsentry/sentry-unity/pull/2685)) - [changelog](https://github.com/getsentry/sentry-native/blob/master/CHANGELOG.md#0142) - [diff](https://github.com/getsentry/sentry-native/compare/0.14.0...0.14.2) +- Bump .NET SDK from v6.6.0-1-g4a85500a to v6.6.0 ([#2698](https://github.com/getsentry/sentry-unity/pull/2698)) + - [changelog](https://github.com/getsentry/sentry-dotnet/blob/main/CHANGELOG.md#660) + - [diff](https://github.com/getsentry/sentry-dotnet/compare/6.6.0-1-g4a85500a...6.6.0) ## 4.3.1 diff --git a/src/Sentry.Unity/Integrations/UnityScopeIntegration.cs b/src/Sentry.Unity/Integrations/UnityScopeIntegration.cs index 84d771261..23c598bfb 100644 --- a/src/Sentry.Unity/Integrations/UnityScopeIntegration.cs +++ b/src/Sentry.Unity/Integrations/UnityScopeIntegration.cs @@ -159,17 +159,19 @@ private void PopulateUnity(Protocol.Unity unity) private void PopulateUser(Scope scope) { - if (scope.User.Id is not null) + // The .NET SDK pre-sets User.Id from its own InstallationId on the root scope in global + // mode. On mobile we want the native SDK's installation id so managed events and native + // crashes share a user identity — overwrite unconditionally when DefaultUserId is set. + if (_options.DefaultUserId is not null) { - return; + scope.User.Id = _options.DefaultUserId; } - // Only set the native installation ID here. The .NET SDK's Enricher handles - // the fallback to InstallationId after the HasUser() check, which allows - // IsEnvironmentUser/SendDefaultPii to set the Username first. - if (_options.DefaultUserId is not null) + // Enricher only applies Environment.UserName when the scope user has no data yet — and + // the pre-set User.Id above trips that gate. Apply it here so IsEnvironmentUser is honored. + if (scope.User.Username is null && _options.SendDefaultPii && _options.IsEnvironmentUser) { - scope.User.Id = _options.DefaultUserId; + scope.User.Username = Environment.UserName; } } } diff --git a/src/sentry-dotnet b/src/sentry-dotnet index 608fc74c4..0140be0a3 160000 --- a/src/sentry-dotnet +++ b/src/sentry-dotnet @@ -1 +1 @@ -Subproject commit 608fc74c4d40fef185473a9a329ae56aa8e0d978 +Subproject commit 0140be0a3b98ee01ff53097a5289bc6e7b703957 diff --git a/test/Sentry.Unity.Tests/UnityEventScopeTests.cs b/test/Sentry.Unity.Tests/UnityEventScopeTests.cs index 6f756e3e4..2bf8103d5 100644 --- a/test/Sentry.Unity.Tests/UnityEventScopeTests.cs +++ b/test/Sentry.Unity.Tests/UnityEventScopeTests.cs @@ -343,19 +343,21 @@ public void UserId_SetIfEmpty() } [Test] - public void UserId_UnchangedIfNonEmpty() + public void UserId_DefaultUserIdOverwritesPreExisting() { - // arrange - var options = new SentryUnityOptions(application: _testApplication) { DefaultUserId = "foo" }; + // arrange - simulates the .NET SDK's GlobalRootScopeIntegration pre-setting User.Id + // before UnityScopeIntegration runs. Unity's native installation id (DefaultUserId) + // must win so managed events and native crashes share the same User.Id. + var options = new SentryUnityOptions(application: _testApplication) { DefaultUserId = "native-id" }; var sut = new UnityScopeUpdater(options, _testApplication); var scope = new Scope(options); - scope.User.Id = "bar"; + scope.User.Id = "dotnet-installation-id"; // act sut.ConfigureScope(scope); // assert - Assert.AreEqual(scope.User.Id, "bar"); + Assert.AreEqual("native-id", scope.User.Id); } [Test] @@ -395,17 +397,19 @@ public void UserId_ScopeSync_TriggeredWhenUserIdSet() } [Test] - public void UserId_ScopeSync_NotTriggeredWhenUserAlreadySet() + public void UserId_ScopeSync_TriggeredEvenWhenUserAlreadySet() { - // arrange - User.Id already set, PopulateUser should early-return - var options = new SentryUnityOptions(application: _testApplication) { DefaultUserId = "should-not-sync" }; + // arrange - simulates the .NET SDK pre-setting User.Id before UnityScopeIntegration runs. + // PopulateUser must still overwrite with DefaultUserId so the native SDK receives the + // native installation id via the scope observer. + var options = new SentryUnityOptions(application: _testApplication) { DefaultUserId = "native-id" }; var observer = new TestScopeObserver(options); options.ScopeObserver = observer; options.EnableScopeSync = true; var sut = new UnityScopeUpdater(options, _testApplication); var scope = new Scope(options); - scope.User.Id = "already-set"; + scope.User.Id = "dotnet-installation-id"; // Reset observer after the initial scope.User.Id set above triggered it observer.LastUser = null; @@ -413,8 +417,9 @@ public void UserId_ScopeSync_NotTriggeredWhenUserAlreadySet() // act sut.ConfigureScope(scope); - // assert - PopulateUser should not have set a new user - Assert.IsNull(observer.LastUser, "ScopeObserver.SetUser should not be called when User.Id is already set"); + // assert - PopulateUser overwrote and synced the native id + Assert.IsNotNull(observer.LastUser, "ScopeObserver.SetUser should be called when DefaultUserId is set"); + Assert.AreEqual("native-id", observer.LastUser!.Id); } [Test]