Skip to content

Release v7.0.0 #4653

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 19 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
380b389
update migration numbers on changelog (#4594)
lucas-zimerman Feb 25, 2025
9ad6fb8
fix(appStart): Align span description with other platforms (#4636)
krystofwoldrich Mar 10, 2025
f5a43d3
chore(deps): Bump Android SDK to v8.3.0 (#4490)
antonis Mar 13, 2025
077a1bd
Merge branch 'main' into v7
antonis Apr 2, 2025
6eaf70f
feat: Bump to Sentry Javascript V9 (#4568)
lucas-zimerman Apr 15, 2025
90aa098
Feat: V7 - JavaScript V9 Add browser session integration (#4732)
lucas-zimerman Apr 15, 2025
a852e28
chore: remove allowSyntheticDefaultImports from TypeScript configurat…
krystofwoldrich Apr 15, 2025
99b2852
Ref: Use main carrier on useEncodePolyfill (#4731)
lucas-zimerman Apr 15, 2025
51f9b96
chore(deps): v7: Bump Android SDK to v8.6.0 (#4663)
antonis Apr 16, 2025
7a15b00
Merge remote-tracking branch 'origin/main' into v7
krystofwoldrich Apr 16, 2025
2c9bcd9
fix(changelog): Move JS and Android deps to the unreleased section (#…
krystofwoldrich Apr 16, 2025
4fabd63
chore: bump JavaScript SDK to v9.12.0 (#4752)
krystofwoldrich Apr 16, 2025
29876df
fix(sdk): Set `{{auto}}` if `user.ip_address` is `undefined` and `sen…
krystofwoldrich Apr 16, 2025
6f2f83f
chore(deps): v7: Bump Android SDK to v8.8.0 (#4755)
antonis Apr 22, 2025
61f61ca
chore(deps): v7: Bump Android SDK to v8.9.0 (#4775)
antonis Apr 24, 2025
261f6a9
Bump Android from 8.9.0 to 8.10.0 (#4781)
antonis Apr 28, 2025
391dc92
chore(typescript): Enable strictNullChecks for the SDK source (#4760)
krystofwoldrich Apr 29, 2025
c68710a
chore(deps): v7: Bump Android SDK to v8.11.0 (#4793)
antonis Apr 30, 2025
10c9244
chore(deps): v7: Bump Android SDK to v8.11.1 (#4796)
antonis May 2, 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
52 changes: 48 additions & 4 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,18 @@

<!-- prettier-ignore-start -->
> [!IMPORTANT]
> If you are upgrading to the `6.x` versions of the Sentry React Native SDK from `5.x` or below,
> If you are upgrading to the `7.x` versions of the Sentry React Native SDK from `6.x` or below,
> make sure you follow our [migration guide](https://docs.sentry.io/platforms/react-native/migration/) first.
<!-- prettier-ignore-end -->

## Unreleased

### Upgrading from 6.x to 7.0

Version 7 of the Sentry React Native SDK primarily introduces API cleanup and version support changes. This update contains behavioral changes that will not be caught by type checkers, linters, or tests, so we recommend carefully reading through the entire migration guide instead of relying on automatic tooling.

Version 7 of the SDK is compatible with Sentry self-hosted versions 24.4.2 or higher (unchanged from v6). Lower versions may continue to work, but may not support all features.

### Fixes

- Avoid silent failure when JS bundle was not created due to Sentry Xcode scripts failure ([#4690](https://github.com/getsentry/sentry-react-native/pull/4690))
Expand All @@ -16,6 +22,12 @@

### Dependencies

- Bump JavaScript SDK from v8.54.0 to v9.12.0 ([#4568](https://github.com/getsentry/sentry-react-native/pull/4568), [#4752](https://github.com/getsentry/sentry-react-native/pull/4752))
- [changelog](https://github.com/getsentry/sentry-javascript/blob/9.12.0/CHANGELOG.md)
- [diff](https://github.com/getsentry/sentry-javascript/compare/8.54.0...9.12.0)
- Bump Android SDK from v7.20.1 to v8.11.1 ([#4490](https://github.com/getsentry/sentry-react-native/pull/4490))
- [changelog](https://github.com/getsentry/sentry-java/blob/main/CHANGELOG.md#8111)
- [diff](https://github.com/getsentry/sentry-java/compare/7.20.1...8.11.1)
- Bump Bundler Plugins from v3.2.2 to v3.3.1 ([#4693](https://github.com/getsentry/sentry-react-native/pull/4693), [#4707](https://github.com/getsentry/sentry-react-native/pull/4707), [#4720](https://github.com/getsentry/sentry-react-native/pull/4720), [#4721](https://github.com/getsentry/sentry-react-native/pull/4721))
- [changelog](https://github.com/getsentry/sentry-javascript-bundler-plugins/blob/main/CHANGELOG.md#331)
- [diff](https://github.com/getsentry/sentry-javascript-bundler-plugins/compare/3.2.2...3.3.1)
Expand All @@ -26,6 +38,37 @@
- [changelog](https://github.com/getsentry/sentry-cocoa/blob/main/CHANGELOG.md#8490)
- [diff](https://github.com/getsentry/sentry-cocoa/compare/8.48.0...8.49.0)

### Major Changes

- Set `{{auto}}` if `user.ip_address` is `undefined` and `sendDefaultPii: true` ([#4466](https://github.com/getsentry/sentry-react-native/pull/4466))
- Exceptions from `captureConsoleIntegration` are now marked as handled: true by default
- `shutdownTimeout` moved from `core` to `@sentry/react-native`
- `hasTracingEnabled` was renamed to `hasSpansEnabled`
- You can no longer drop spans or return null on `beforeSendSpan` hook

### Removed types

- TransactionNamingScheme
- Request
- Scope (prefer using the Scope class)

### Other removed items.

- `autoSessionTracking` from options.
To enable session tracking, ensure that `enableAutoSessionTracking` is enabled.
- `enableTracing`. Instead, set `tracesSampleRate` to a value greater than `zero` to `enable tracing`, `0` to keep tracing integrations active without sampling, or `undefined` to disable the performance integration.
- `getCurrentHub()`, `Hub`, and `getCurrentHubShim()`
- `spanId` from propagation `context`
- metrics API
- `transactionContext` from `samplingContext`
- `@sentry/utils` package, the exports were moved to `@sentry/core`
- Standalone `Client` interface & deprecate `BaseClient`

## Other Changes

- Fork `scope` if custom scope is passed to `startSpanManual` or `startSpan`
- On React Native Web, `browserSessionIntegration` is added when `enableAutoSessionTracking` is set to `True` ([#4732](https://github.com/getsentry/sentry-react-native/pull/4732))

## 6.11.0-beta.0

### Features
Expand Down Expand Up @@ -181,6 +224,10 @@

To learn more about the available configuration options visit [the documentation](https://docs.sentry.io/platforms/react-native/manual-setup/expo/gradle).

### Changes

Change `Cold/Warm App Start` span description to `Cold/Warm Start` ([#4636](https://github.com/getsentry/sentry-react-native/pull/4636))

### Fixes

- Remove `error:` prefix from `collect-modules.sh` to avoid failing iOS builds ([#4570](https://github.com/getsentry/sentry-react-native/pull/4570))
Expand All @@ -191,9 +238,6 @@

### Dependencies

- Bump Android SDK from v7.20.1 to v7.22.0 ([#4529](https://github.com/getsentry/sentry-react-native/pull/4529))
- [changelog](https://github.com/getsentry/sentry-java/blob/7.x.x/CHANGELOG.md#7220)
- [diff](https://github.com/getsentry/sentry-java/compare/7.20.1...7.22.0)
- Bump Cocoa SDK from v8.44.0 to v8.45.0 ([#4537](https://github.com/getsentry/sentry-react-native/pull/4537))
- [changelog](https://github.com/getsentry/sentry-cocoa/blob/main/CHANGELOG.md#8450)
- [diff](https://github.com/getsentry/sentry-cocoa/compare/8.44.0...8.45.0)
Expand Down
2 changes: 1 addition & 1 deletion dev-packages/e2e-tests/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
"devDependencies": {
"@babel/preset-env": "^7.25.3",
"@babel/preset-typescript": "^7.18.6",
"@sentry/core": "8.54.0",
"@sentry/core": "9.12.0",
"@sentry/react-native": "6.11.0-beta.0",
"@types/node": "^20.9.3",
"@types/react": "^18.2.64",
Expand Down
4 changes: 4 additions & 0 deletions dev-packages/type-check/ts3.8-test/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ declare global {
interface IDBObjectStore {}
interface Window {
fetch: any;
setTimeout: any;
document: any;
}
interface ShadowRoot {}
interface BufferSource {}
Expand All @@ -19,6 +21,8 @@ declare global {
redirectCount: number;
}
interface PerformanceEntry {}
interface Performance {}
interface PerformanceNavigationTiming {}
}

declare module 'react-native' {
Expand Down
2 changes: 1 addition & 1 deletion packages/core/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -54,5 +54,5 @@ android {

dependencies {
implementation 'com.facebook.react:react-native:+'
api 'io.sentry:sentry-android:7.22.5'
api 'io.sentry:sentry-android:8.11.1'
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,12 @@
import com.facebook.react.bridge.WritableNativeMap;
import com.facebook.react.common.JavascriptException;
import io.sentry.Breadcrumb;
import io.sentry.HubAdapter;
import io.sentry.ILogger;
import io.sentry.IScope;
import io.sentry.ISentryExecutorService;
import io.sentry.ISerializer;
import io.sentry.Integration;
import io.sentry.ScopesAdapter;
import io.sentry.Sentry;
import io.sentry.SentryDate;
import io.sentry.SentryDateProvider;
Expand Down Expand Up @@ -87,6 +87,7 @@
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.concurrent.CountDownLatch;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
Expand Down Expand Up @@ -516,7 +517,7 @@ public void fetchNativeFrames(Promise promise) {
}

public void captureReplay(boolean isHardCrash, Promise promise) {
Sentry.getCurrentHub().getOptions().getReplayController().captureReplay(isHardCrash);
Sentry.getCurrentScopes().getOptions().getReplayController().captureReplay(isHardCrash);
promise.resolve(getCurrentReplayId());
}

Expand Down Expand Up @@ -612,7 +613,7 @@ public void fetchViewHierarchy(Promise promise) {
return;
}

ISerializer serializer = HubAdapter.getInstance().getOptions().getSerializer();
ISerializer serializer = ScopesAdapter.getInstance().getOptions().getSerializer();
final @Nullable byte[] bytes =
JsonSerializationUtils.bytesFrom(serializer, logger, viewHierarchy);
if (bytes == null) {
Expand Down Expand Up @@ -666,10 +667,6 @@ public void setUser(final ReadableMap userKeys, final ReadableMap userDataKeys)
if (userKeys.hasKey("ip_address")) {
userInstance.setIpAddress(userKeys.getString("ip_address"));
}

if (userKeys.hasKey("segment")) {
userInstance.setSegment(userKeys.getString("segment"));
}
}

if (userDataKeys != null) {
Expand Down Expand Up @@ -831,8 +828,7 @@ private void initializeAndroidProfiler() {
(int) SECONDS.toMicros(1) / profilingTracesHz,
new SentryFrameMetricsCollector(reactApplicationContext, logger, buildInfo),
executorService,
logger,
buildInfo);
logger);
}

public WritableMap startProfiling(boolean platformProfilers) {
Expand All @@ -856,7 +852,7 @@ public WritableMap startProfiling(boolean platformProfilers) {
}

public WritableMap stopProfiling() {
final boolean isDebug = HubAdapter.getInstance().getOptions().isDebug();
final boolean isDebug = ScopesAdapter.getInstance().getOptions().isDebug();
final WritableMap result = new WritableNativeMap();
File output = null;
try {
Expand Down Expand Up @@ -942,7 +938,7 @@ private String readStringFromFile(File path) throws IOException {
}

public void fetchNativeDeviceContexts(Promise promise) {
final @NotNull SentryOptions options = HubAdapter.getInstance().getOptions();
final @NotNull SentryOptions options = ScopesAdapter.getInstance().getOptions();
final @Nullable Context context = this.getReactApplicationContext().getApplicationContext();
final @Nullable IScope currentScope = InternalSentrySdk.getCurrentScope();
fetchNativeDeviceContexts(promise, options, context, currentScope);
Expand Down Expand Up @@ -979,7 +975,8 @@ protected void fetchNativeDeviceContexts(
}

public void fetchNativeSdkInfo(Promise promise) {
final @Nullable SdkVersion sdkVersion = HubAdapter.getInstance().getOptions().getSdkVersion();
final @Nullable SdkVersion sdkVersion =
ScopesAdapter.getInstance().getOptions().getSdkVersion();
if (sdkVersion == null) {
promise.resolve(null);
} else {
Expand Down Expand Up @@ -1058,14 +1055,14 @@ private void addPackages(SentryEvent event, SdkVersion sdk) {
if (eventSdk != null
&& "sentry.javascript.react-native".equals(eventSdk.getName())
&& sdk != null) {
List<SentryPackage> sentryPackages = sdk.getPackages();
Set<SentryPackage> sentryPackages = sdk.getPackageSet();
if (sentryPackages != null) {
for (SentryPackage sentryPackage : sentryPackages) {
eventSdk.addPackage(sentryPackage.getName(), sentryPackage.getVersion());
}
}

List<String> integrations = sdk.getIntegrations();
Set<String> integrations = sdk.getIntegrationSet();
if (integrations != null) {
for (String integration : integrations) {
eventSdk.addIntegration(integration);
Expand Down
17 changes: 8 additions & 9 deletions packages/core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -66,21 +66,20 @@
},
"dependencies": {
"@sentry/babel-plugin-component-annotate": "3.3.1",
"@sentry/browser": "8.54.0",
"@sentry/browser": "9.12.0",
"@sentry/cli": "2.43.0",
"@sentry/core": "8.54.0",
"@sentry/react": "8.54.0",
"@sentry/types": "8.54.0",
"@sentry/utils": "8.54.0"
"@sentry/core": "9.12.0",
"@sentry/react": "9.12.0",
"@sentry/types": "9.12.0"
},
"devDependencies": {
"@babel/core": "^7.25.2",
"@expo/metro-config": "0.19.5",
"@mswjs/interceptors": "^0.25.15",
"@react-native/babel-preset": "0.77.1",
"@sentry-internal/eslint-config-sdk": "8.54.0",
"@sentry-internal/eslint-plugin-sdk": "8.54.0",
"@sentry-internal/typescript": "8.54.0",
"@sentry-internal/eslint-config-sdk": "9.12.0",
"@sentry-internal/eslint-plugin-sdk": "9.12.0",
"@sentry-internal/typescript": "9.12.0",
"@sentry/wizard": "4.7.0",
"@testing-library/react-native": "^12.7.2",
"@types/jest": "^29.5.13",
Expand Down Expand Up @@ -110,7 +109,7 @@
"react-native": "0.77.1",
"react-test-renderer": "^18.3.1",
"rimraf": "^4.1.1",
"ts-jest": "^29.1.1",
"ts-jest": "^29.3.1",
"typescript": "4.9.5",
"uglify-js": "^3.17.4",
"uuid": "^9.0.1",
Expand Down
2 changes: 1 addition & 1 deletion packages/core/plugin/src/withSentry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ interface PluginProps {
const withSentryPlugin: ConfigPlugin<PluginProps | void> = (config, props) => {
const sentryProperties = getSentryProperties(props);

if (props && props.authToken) {
if (props?.authToken) {
// If not removed, the plugin config with the authToken will be written to the application package
delete props.authToken;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ export function withSentryAndroidGradlePlugin(
const withSentryProjectBuildGradle = (config: any): any => {
return withProjectBuildGradle(config, (projectBuildGradle: any) => {
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
if (!projectBuildGradle.modResults || !projectBuildGradle.modResults.contents) {
if (!projectBuildGradle.modResults?.contents) {
warnOnce('android/build.gradle content is missing or undefined.');
return config;
}
Expand Down
14 changes: 13 additions & 1 deletion packages/core/src/js/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,14 @@ import type {
TransportMakeRequestResponse,
UserFeedback,
} from '@sentry/core';
import { BaseClient, dateTimestampInSeconds, logger, SentryError } from '@sentry/core';
import {
addAutoIpAddressToSession,
addAutoIpAddressToUser,
BaseClient,
dateTimestampInSeconds,
logger,
SentryError,
} from '@sentry/core';
import { Alert } from 'react-native';

import { getDevServer } from './integrations/debugsymbolicatorutils';
Expand Down Expand Up @@ -48,6 +55,11 @@ export class ReactNativeClient extends BaseClient<ReactNativeClientOptions> {
super(options);

this._outcomesBuffer = [];

if (options.sendDefaultPii === true) {
this.on('postprocessEvent', addAutoIpAddressToUser);
this.on('beforeSendSession', addAutoIpAddressToSession);
}
}

/**
Expand Down
38 changes: 18 additions & 20 deletions packages/core/src/js/feedback/FeedbackWidget.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,7 @@ import { base64ToUint8Array, feedbackAlertDialog, isValidEmail } from './utils'
* Implements a feedback form screen that sends feedback to Sentry using Sentry.captureFeedback.
*/
export class FeedbackWidget extends React.Component<FeedbackWidgetProps, FeedbackWidgetState> {
public static defaultProps: Partial<FeedbackWidgetProps> = {
...defaultConfiguration
}
public static defaultProps = defaultConfiguration;

private static _savedState: Omit<FeedbackWidgetState, 'isVisible'> = {
name: '',
Expand Down Expand Up @@ -67,7 +65,7 @@ export class FeedbackWidget extends React.Component<FeedbackWidgetProps, Feedbac
public handleFeedbackSubmit: () => void = () => {
const { name, email, description } = this.state;
const { onSubmitSuccess, onSubmitError, onFormSubmitted } = this.props;
const text: FeedbackTextConfiguration = this.props;
const text = this.props;

const trimmedName = name?.trim();
const trimmedEmail = email?.trim();
Expand Down Expand Up @@ -119,14 +117,14 @@ export class FeedbackWidget extends React.Component<FeedbackWidgetProps, Feedbac

public onScreenshotButtonPress: () => void = async () => {
if (!this.state.filename && !this.state.attachment) {
const imagePickerConfiguration: ImagePickerConfiguration = this.props;
if (imagePickerConfiguration.imagePicker) {
const launchImageLibrary = imagePickerConfiguration.imagePicker.launchImageLibraryAsync
const { imagePicker } = this.props;
if (imagePicker) {
const launchImageLibrary = imagePicker.launchImageLibraryAsync
// expo-image-picker library is available
? () => imagePickerConfiguration.imagePicker.launchImageLibraryAsync({ mediaTypes: ['images'], base64: isWeb() })
? () => imagePicker.launchImageLibraryAsync?.({ mediaTypes: ['images'], base64: isWeb() })
// react-native-image-picker library is available
: imagePickerConfiguration.imagePicker.launchImageLibrary
? () => imagePickerConfiguration.imagePicker.launchImageLibrary({ mediaType: 'photo', includeBase64: isWeb() })
: imagePicker.launchImageLibrary
? () => imagePicker.launchImageLibrary?.({ mediaType: 'photo', includeBase64: isWeb() })
: null;
if (!launchImageLibrary) {
logger.warn('No compatible image picker library found. Please provide a valid image picker library.');
Expand All @@ -140,22 +138,22 @@ export class FeedbackWidget extends React.Component<FeedbackWidgetProps, Feedbac
}

const result = await launchImageLibrary();
if (result.assets && result.assets.length > 0) {
if (result?.assets && result.assets.length > 0) {
if (isWeb()) {
const filename = result.assets[0].fileName;
const imageUri = result.assets[0].uri;
const base64 = result.assets[0].base64;
const data = base64ToUint8Array(base64);
if (data != null) {
const filename = result.assets[0]?.fileName;
const imageUri = result.assets[0]?.uri;
const base64 = result.assets[0]?.base64;
const data = base64 ? base64ToUint8Array(base64) : undefined;
if (data) {
this.setState({ filename, attachment: data, attachmentUri: imageUri });
} else {
logger.error('Failed to read image data on the web');
}
} else {
const filename = result.assets[0].fileName;
const imageUri = result.assets[0].uri;
getDataFromUri(imageUri).then((data) => {
if (data != null) {
const filename = result.assets[0]?.fileName;
const imageUri = result.assets[0]?.uri;
imageUri && getDataFromUri(imageUri).then((data) => {
if (data) {
this.setState({ filename, attachment: data, attachmentUri: imageUri });
} else {
logger.error('Failed to read image data from uri:', imageUri);
Expand Down
Loading