@sentry/wizard 6.4.0 → 6.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -0
- package/dist/e2e-tests/tests/expo.test.js +9 -2
- package/dist/e2e-tests/tests/expo.test.js.map +1 -1
- package/dist/e2e-tests/tests/react-native.test.js +9 -2
- package/dist/e2e-tests/tests/react-native.test.js.map +1 -1
- package/dist/src/android/android-wizard.js +9 -1
- package/dist/src/android/android-wizard.js.map +1 -1
- package/dist/src/android/manifest.d.ts +1 -1
- package/dist/src/android/manifest.js +2 -2
- package/dist/src/android/manifest.js.map +1 -1
- package/dist/src/android/templates.d.ts +1 -1
- package/dist/src/android/templates.js +4 -1
- package/dist/src/android/templates.js.map +1 -1
- package/dist/src/react-native/javascript.d.ts +6 -4
- package/dist/src/react-native/javascript.js +11 -7
- package/dist/src/react-native/javascript.js.map +1 -1
- package/dist/src/react-native/react-native-wizard.js +12 -3
- package/dist/src/react-native/react-native-wizard.js.map +1 -1
- package/dist/src/react-native/xcode.d.ts +2 -2
- package/dist/src/react-native/xcode.js +11 -4
- package/dist/src/react-native/xcode.js.map +1 -1
- package/dist/src/version.d.ts +1 -1
- package/dist/src/version.js +1 -1
- package/dist/src/version.js.map +1 -1
- package/dist/test/react-native/javascript.test.js +225 -0
- package/dist/test/react-native/javascript.test.js.map +1 -1
- package/dist/test/react-native/xcode.test.js +21 -4
- package/dist/test/react-native/xcode.test.js.map +1 -1
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"javascript.test.js","sourceRoot":"","sources":["../../../test/react-native/javascript.test.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n addSentryInitWithSdkImport,\n checkAndWrapRootComponent,\n doesContainSentryWrap,\n doesJsCodeIncludeSdkSentryImport,\n SentryWrapResult,\n} from '../../src/react-native/javascript';\n// @ts-expect-error - magicast is ESM and TS complains about that. It works though\nimport { generateCode, parseModule } from 'magicast';\nimport * as t from '@babel/types';\nimport { describe, expect, it } from 'vitest';\n\ndescribe('react-native javascript', () => {\n describe('addSentryInitWithSdkImport', () => {\n it('adds sdk import and sentry init under last import in the file', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(\n expectedOutput,\n );\n });\n\n it('adds sdk import and sentry init under last import in the file and enables session replay', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Configure Session Replay\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.mobileReplayIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init under last import in the file and enables feedback widget', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n integrations: [Sentry.feedbackIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableFeedbackWidget: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init under last import in the file and enables session replay and feedback widget', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Configure Session Replay\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.mobileReplayIntegration(), Sentry.feedbackIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: true,\n enableFeedbackWidget: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('does not add sdk import and sentry init in the file without imports', () => {\n const input = `export const test = 'test';`;\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(input);\n });\n\n it('does not add sdk import and sentry init in the empty file', () => {\n const input = '';\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(input);\n });\n });\n\n describe('doesJsCodeIncludeSdkSentryImport', () => {\n it('returns true if code has sdk import', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(true);\n });\n\n it('returns true if code has sdk require', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nconst Sentry = require('@sentry/react-native');\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(true);\n });\n\n it('returns false if code does not have sdk import', () => {\n const input = `export const test = 'test';`;\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(false);\n });\n\n it('returns false for empty file', () => {\n const input = '';\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(false);\n });\n });\n\n describe('addSentryWrap', () => {\n it('wraps the root app component', () => {\n const mod = parseModule(`import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`);\n\n const expectedOutput = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(App);`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app component', () => {\n const mod = parseModule(`import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default AnotheWrapper.wrap(App);`);\n\n const expectedOutput = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(AnotheWrapper.wrap(App));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app named function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app named function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default Another.wrapper(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n});`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(Another.wrapper(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n}));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app anonymous function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default () => {\n return (\n <View>\n Test App\n </View>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app anonymous function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default Another.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n});`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(Another.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n}));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a complex root function', () => {\n // This is the default export for a new Expo 52 project\n const mod =\n parseModule(`import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';\nimport { useFonts } from 'expo-font';\nimport { Stack } from 'expo-router';\nimport * as SplashScreen from 'expo-splash-screen';\nimport { StatusBar } from 'expo-status-bar';\nimport { useEffect } from 'react';\nimport 'react-native-reanimated';\n\nimport { useColorScheme } from '@/hooks/useColorScheme';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://sentry.io/123',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\n// Prevent the splash screen from auto-hiding before asset loading is complete.\nSplashScreen.preventAutoHideAsync();\n\nexport default function RootLayout() {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n}\n`);\n\n const expectedOutput = `import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';\nimport { useFonts } from 'expo-font';\nimport { Stack } from 'expo-router';\nimport * as SplashScreen from 'expo-splash-screen';\nimport { StatusBar } from 'expo-status-bar';\nimport { useEffect } from 'react';\nimport 'react-native-reanimated';\n\nimport { useColorScheme } from '@/hooks/useColorScheme';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://sentry.io/123',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\n// Prevent the splash screen from auto-hiding before asset loading is complete.\nSplashScreen.preventAutoHideAsync();\n\nexport default Sentry.wrap(function RootLayout() {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app anonymous complex function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default () => {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(() => {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a default class export', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default class RootLayout extends React.Component {\n render() {\n return (\n <View>\n Test App\n </View>\n );\n }\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(class RootLayout extends React.Component {\n render() {\n return (\n <View>\n Test App\n </View>\n );\n }\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('does not wrap a root app component if not found', () => {\n const input = `import * as React from 'react';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport { App };`;\n const mod = parseModule(input);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.NotFound);\n expect(generateCode(mod.$ast).code).toBe(input);\n });\n\n it('does not wrap a root app component if already wrapped', () => {\n const input = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(App);`;\n const mod = parseModule(input);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.AlreadyWrapped);\n expect(generateCode(mod.$ast).code).toBe(input);\n });\n\n it('does not wrap the root app component in an empty file', () => {\n const mod = parseModule(``);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.NotFound);\n expect(generateCode(mod.$ast).code).toBe(``);\n });\n });\n\n it('does detect Sentry.wrap if exists', () => {\n const mod = parseModule(`export default Sentry.wrap(App);`);\n\n const result = doesContainSentryWrap(mod.$ast as t.Program);\n\n expect(result).toBeTruthy();\n });\n\n it('does not detect Sentry.wrap if not present', () => {\n const mod = parseModule(`export default App;`);\n\n const result = doesContainSentryWrap(mod.$ast as t.Program);\n\n expect(result).toBeFalsy();\n });\n});\n"]}
|
|
1
|
+
{"version":3,"file":"javascript.test.js","sourceRoot":"","sources":["../../../test/react-native/javascript.test.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n addSentryInitWithSdkImport,\n checkAndWrapRootComponent,\n doesContainSentryWrap,\n doesJsCodeIncludeSdkSentryImport,\n SentryWrapResult,\n} from '../../src/react-native/javascript';\n// @ts-expect-error - magicast is ESM and TS complains about that. It works though\nimport { generateCode, parseModule } from 'magicast';\nimport * as t from '@babel/types';\nimport { describe, expect, it } from 'vitest';\n\ndescribe('react-native javascript', () => {\n describe('addSentryInitWithSdkImport', () => {\n it('adds sdk import and sentry init under last import in the file', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: false,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(\n expectedOutput,\n );\n });\n\n it('adds sdk import and sentry init under last import in the file and enables session replay', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: false,\n\n // Configure Session Replay\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.mobileReplayIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init under last import in the file and enables feedback widget', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: false,\n integrations: [Sentry.feedbackIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableFeedbackWidget: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init under last import in the file and enables logs', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableLogs: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init with logs disabled', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: false,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableLogs: false,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init under last import in the file and enables session replay and feedback widget', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: false,\n\n // Configure Session Replay\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.mobileReplayIntegration(), Sentry.feedbackIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: true,\n enableFeedbackWidget: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init with all features enabled', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: true,\n\n // Configure Session Replay\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.mobileReplayIntegration(), Sentry.feedbackIntegration()],\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: true,\n enableFeedbackWidget: true,\n enableLogs: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('adds sdk import and sentry init with logs enabled and other features disabled', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n const expectedOutput = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'dsn',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // Enable Logs\n enableLogs: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n addSentryInitWithSdkImport(input, {\n dsn: 'dsn',\n enableSessionReplay: false,\n enableFeedbackWidget: false,\n enableLogs: true,\n }),\n ).toBe(expectedOutput);\n });\n\n it('does not add sdk import and sentry init in the file without imports', () => {\n const input = `export const test = 'test';`;\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(input);\n });\n\n it('does not add sdk import and sentry init in the empty file', () => {\n const input = '';\n expect(addSentryInitWithSdkImport(input, { dsn: 'dsn' })).toBe(input);\n });\n });\n\n describe('doesJsCodeIncludeSdkSentryImport', () => {\n it('returns true if code has sdk import', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nimport * as Sentry from '@sentry/react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(true);\n });\n\n it('returns true if code has sdk require', () => {\n const input = `import * as React from 'react';\n\nconst test = 'test';\n\nimport { View } from 'react-native';\nconst Sentry = require('@sentry/react-native');\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`;\n\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(true);\n });\n\n it('returns false if code does not have sdk import', () => {\n const input = `export const test = 'test';`;\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(false);\n });\n\n it('returns false for empty file', () => {\n const input = '';\n expect(\n doesJsCodeIncludeSdkSentryImport(input, {\n sdkPackageName: '@sentry/react-native',\n }),\n ).toBe(false);\n });\n });\n\n describe('addSentryWrap', () => {\n it('wraps the root app component', () => {\n const mod = parseModule(`import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default App;`);\n\n const expectedOutput = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(App);`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app component', () => {\n const mod = parseModule(`import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default AnotheWrapper.wrap(App);`);\n\n const expectedOutput = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(AnotheWrapper.wrap(App));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app named function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app named function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default Another.wrapper(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n});`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(Another.wrapper(function RootLayout() {\n return (\n <View>\n Test App\n </View>\n );\n}));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app anonymous function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default () => {\n return (\n <View>\n Test App\n </View>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a wrapped root app anonymous function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default Another.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n});`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(Another.wrap(() => {\n return (\n <View>\n Test App\n </View>\n );\n}));`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a complex root function', () => {\n // This is the default export for a new Expo 52 project\n const mod =\n parseModule(`import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';\nimport { useFonts } from 'expo-font';\nimport { Stack } from 'expo-router';\nimport * as SplashScreen from 'expo-splash-screen';\nimport { StatusBar } from 'expo-status-bar';\nimport { useEffect } from 'react';\nimport 'react-native-reanimated';\n\nimport { useColorScheme } from '@/hooks/useColorScheme';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://sentry.io/123',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\n// Prevent the splash screen from auto-hiding before asset loading is complete.\nSplashScreen.preventAutoHideAsync();\n\nexport default function RootLayout() {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n}\n`);\n\n const expectedOutput = `import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';\nimport { useFonts } from 'expo-font';\nimport { Stack } from 'expo-router';\nimport * as SplashScreen from 'expo-splash-screen';\nimport { StatusBar } from 'expo-status-bar';\nimport { useEffect } from 'react';\nimport 'react-native-reanimated';\n\nimport { useColorScheme } from '@/hooks/useColorScheme';\nimport * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://sentry.io/123',\n\n // Adds more context data to events (IP address, cookies, user, etc.)\n // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/\n sendDefaultPii: true,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: __DEV__,\n});\n\n// Prevent the splash screen from auto-hiding before asset loading is complete.\nSplashScreen.preventAutoHideAsync();\n\nexport default Sentry.wrap(function RootLayout() {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a root app anonymous complex function', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default () => {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(() => {\n const colorScheme = useColorScheme();\n const [loaded] = useFonts({\n SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),\n });\n\n useEffect(() => {\n if (loaded) {\n SplashScreen.hideAsync();\n }\n }, [loaded]);\n\n if (!loaded) {\n return null;\n }\n\n return (\n <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>\n <Stack>\n <Stack.Screen name=\"(tabs)\" options={{ headerShown: false }} />\n <Stack.Screen name=\"+not-found\" />\n </Stack>\n <StatusBar style=\"auto\" />\n </ThemeProvider>\n );\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('wraps a default class export', () => {\n const mod = parseModule(`import * as Sentry from '@sentry/react-native';\n\nexport default class RootLayout extends React.Component {\n render() {\n return (\n <View>\n Test App\n </View>\n );\n }\n}`);\n\n const expectedOutput = `import * as Sentry from '@sentry/react-native';\n\nexport default Sentry.wrap(class RootLayout extends React.Component {\n render() {\n return (\n <View>\n Test App\n </View>\n );\n }\n});`;\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.Success);\n expect(generateCode(mod.$ast).code).toBe(expectedOutput);\n });\n\n it('does not wrap a root app component if not found', () => {\n const input = `import * as React from 'react';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport { App };`;\n const mod = parseModule(input);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.NotFound);\n expect(generateCode(mod.$ast).code).toBe(input);\n });\n\n it('does not wrap a root app component if already wrapped', () => {\n const input = `import * as React from 'react';\nimport * as Sentry from '@sentry/react-native';\n\nimport { View } from 'react-native';\n\nconst App = () => {\n return (\n <View>\n Test App\n </View>\n );\n};\n\nexport default Sentry.wrap(App);`;\n const mod = parseModule(input);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.AlreadyWrapped);\n expect(generateCode(mod.$ast).code).toBe(input);\n });\n\n it('does not wrap the root app component in an empty file', () => {\n const mod = parseModule(``);\n\n const result = checkAndWrapRootComponent(mod);\n\n expect(result).toBe(SentryWrapResult.NotFound);\n expect(generateCode(mod.$ast).code).toBe(``);\n });\n });\n\n it('does detect Sentry.wrap if exists', () => {\n const mod = parseModule(`export default Sentry.wrap(App);`);\n\n const result = doesContainSentryWrap(mod.$ast as t.Program);\n\n expect(result).toBeTruthy();\n });\n\n it('does not detect Sentry.wrap if not present', () => {\n const mod = parseModule(`export default App;`);\n\n const result = doesContainSentryWrap(mod.$ast as t.Program);\n\n expect(result).toBeFalsy();\n });\n});\n"]}
|
|
@@ -37,6 +37,8 @@ vitest_1.vi.mock('@clack/prompts', async () => ({
|
|
|
37
37
|
__esModule: true,
|
|
38
38
|
...(await vitest_1.vi.importActual('@clack/prompts')),
|
|
39
39
|
}));
|
|
40
|
+
const rnVersionWithQuotes = '0.81.0';
|
|
41
|
+
const rnVersionWithoutQuotes = '0.81.1';
|
|
40
42
|
(0, vitest_1.describe)('react-native xcode', () => {
|
|
41
43
|
(0, vitest_1.beforeEach)(() => {
|
|
42
44
|
vitest_1.vi.spyOn(clack.log, 'error').mockImplementation(() => {
|
|
@@ -63,7 +65,22 @@ WITH_ENVIRONMENT="../node_modules/react-native/scripts/xcode/with-environment.sh
|
|
|
63
65
|
REACT_NATIVE_XCODE="../node_modules/react-native/scripts/react-native-xcode.sh"
|
|
64
66
|
|
|
65
67
|
/bin/sh -c "$WITH_ENVIRONMENT \\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\\""`;
|
|
66
|
-
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input)).toBe(expectedOutput);
|
|
68
|
+
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input, rnVersionWithQuotes)).toBe(expectedOutput);
|
|
69
|
+
});
|
|
70
|
+
(0, vitest_1.it)('does not add with-environment.sh parameter quotes for RN version >= 0.81.1 to rn bundle build phase', () => {
|
|
71
|
+
const input = `set -e
|
|
72
|
+
|
|
73
|
+
WITH_ENVIRONMENT="../node_modules/react-native/scripts/xcode/with-environment.sh"
|
|
74
|
+
REACT_NATIVE_XCODE="../node_modules/react-native/scripts/react-native-xcode.sh"
|
|
75
|
+
|
|
76
|
+
/bin/sh -c "$WITH_ENVIRONMENT $REACT_NATIVE_XCODE"`;
|
|
77
|
+
const expectedOutput = `set -e
|
|
78
|
+
|
|
79
|
+
WITH_ENVIRONMENT="../node_modules/react-native/scripts/xcode/with-environment.sh"
|
|
80
|
+
REACT_NATIVE_XCODE="../node_modules/react-native/scripts/react-native-xcode.sh"
|
|
81
|
+
|
|
82
|
+
/bin/sh -c "$WITH_ENVIRONMENT /bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE"`;
|
|
83
|
+
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input, rnVersionWithoutQuotes)).toBe(expectedOutput);
|
|
67
84
|
});
|
|
68
85
|
(0, vitest_1.it)('does not add sentry cli to rn bundle build phase if $REACT_NATIVE_XCODE is not present and shows code snippet', () => {
|
|
69
86
|
const input = `set -e
|
|
@@ -72,7 +89,7 @@ REACT_NATIVE_XCODE="../node_modules/react-native/scripts/react-native-xcode.sh"
|
|
|
72
89
|
REACT_NATIVE_XCODE="../node_modules/react-native/scripts/react-native-xcode.sh"
|
|
73
90
|
|
|
74
91
|
/bin/sh -c "$WITH_ENVIRONMENT $NOT_REACT_NATIVE_XCODE"`;
|
|
75
|
-
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input)).toEqual(new xcode_1.ErrorPatchSnippet((0, clack_1.makeCodeSnippet)(true, (unchanged, plus, _minus) => {
|
|
92
|
+
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input, rnVersionWithQuotes)).toEqual(new xcode_1.ErrorPatchSnippet((0, clack_1.makeCodeSnippet)(true, (unchanged, plus, _minus) => {
|
|
76
93
|
return unchanged(`WITH_ENVIRONMENT="$REACT_NATIVE_PATH/scripts/xcode/with-environment.sh"
|
|
77
94
|
REACT_NATIVE_XCODE="$REACT_NATIVE_PATH/scripts/react-native-xcode.sh"
|
|
78
95
|
|
|
@@ -164,7 +181,7 @@ fi
|
|
|
164
181
|
|
|
165
182
|
/bin/sh \`"$NODE_BINARY" --print "require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'"\` \`"$NODE_BINARY" --print "require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'"\`
|
|
166
183
|
`;
|
|
167
|
-
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input)).toBe(expectedOutput);
|
|
184
|
+
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input, rnVersionWithQuotes)).toBe(expectedOutput);
|
|
168
185
|
});
|
|
169
186
|
(0, vitest_1.it)('if patching fails it does not add sentry cli to expo bundle build phase and shows code snippet', () => {
|
|
170
187
|
const input = `
|
|
@@ -186,7 +203,7 @@ if [[ -z "$ENTRY_FILE" ]]; then
|
|
|
186
203
|
export ENTRY_FILE="$("$NODE_BINARY" -e "require('expo/scripts/resolveAppEntry')" "$PROJECT_ROOT" ios absolute | tail -n 1)"
|
|
187
204
|
fi
|
|
188
205
|
`;
|
|
189
|
-
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input)).toEqual(new xcode_1.ErrorPatchSnippet((0, clack_1.makeCodeSnippet)(true, (unchanged, plus, _minus) => {
|
|
206
|
+
(0, vitest_1.expect)((0, xcode_1.addSentryWithBundledScriptsToBundleShellScript)(input, rnVersionWithQuotes)).toEqual(new xcode_1.ErrorPatchSnippet((0, clack_1.makeCodeSnippet)(true, (unchanged, plus, _minus) => {
|
|
190
207
|
return unchanged(`${plus(`/bin/sh \`"$NODE_BINARY" --print "require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'"\``)} \`"$NODE_BINARY" --print "require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'"\``);
|
|
191
208
|
})));
|
|
192
209
|
(0, vitest_1.expect)(clack.log.error).toHaveBeenCalledWith(`Failed to patch ${chalk_1.default.cyan('Bundle React Native code and images')} build phase.`);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"xcode.test.js","sourceRoot":"","sources":["../../../test/react-native/xcode.test.ts"],"names":[],"mappings":"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","sourcesContent":["/* eslint-disable no-useless-escape */\nimport { describe, expect, it, afterEach, beforeEach, vi } from 'vitest';\nimport {\n addSentryWithBundledScriptsToBundleShellScript,\n doesBundlePhaseIncludeSentry,\n findBundlePhase,\n findDebugFilesUploadPhase,\n ErrorPatchSnippet,\n} from '../../src/react-native/xcode';\nimport chalk from 'chalk';\nimport { makeCodeSnippet } from '../../src/utils/clack';\n// @ts-expect-error - clack is ESM and TS complains about that. It works though\nimport * as clack from '@clack/prompts';\n\nvi.mock('@clack/prompts', async () => ({\n __esModule: true,\n ...(await vi.importActual<typeof clack>('@clack/prompts')),\n}));\n\ndescribe('react-native xcode', () => {\n beforeEach(() => {\n vi.spyOn(clack.log, 'error').mockImplementation(() => {\n /* empty */\n });\n });\n\n afterEach(() => {\n vi.clearAllMocks();\n });\n\n describe('addSentryBundledScriptsToBundleShellScript', () => {\n it('adds sentry cli to rn bundle build phase', () => {\n const input = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT $REACT_NATIVE_XCODE\"`;\n // actual shell script looks like this:\n // /bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n // but during parsing xcode library removes the quotes\n const expectedOutput = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\\\\\"\"`;\n\n expect(addSentryWithBundledScriptsToBundleShellScript(input)).toBe(\n expectedOutput,\n );\n });\n\n it('does not add sentry cli to rn bundle build phase if $REACT_NATIVE_XCODE is not present and shows code snippet', () => {\n const input = `set -e\n \n WITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\n REACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n \n /bin/sh -c \"$WITH_ENVIRONMENT $NOT_REACT_NATIVE_XCODE\"`;\n\n expect(addSentryWithBundledScriptsToBundleShellScript(input)).toEqual(\n new ErrorPatchSnippet(\n makeCodeSnippet(true, (unchanged, plus, _minus) => {\n return unchanged(`WITH_ENVIRONMENT=\"$REACT_NATIVE_PATH/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"$REACT_NATIVE_PATH/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT ${plus(\n `\\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh `,\n )}$REACT_NATIVE_XCODE${plus(`\\\\\"`)}\"\n`);\n }),\n ),\n );\n expect(clack.log.error).toHaveBeenCalledWith(\n `Failed to patch ${chalk.cyan(\n 'Bundle React Native code and images',\n )} build phase.`,\n );\n });\n\n it('adds sentry cli to expo bundle build phase', () => {\n const input = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n\nif [[ -z \"$CLI_PATH\" ]]; then\n # Use Expo CLI\n export CLI_PATH=\"$(\"$NODE_BINARY\" --print \"require.resolve('@expo/cli', { paths: [require.resolve('expo/package.json')] })\")\"\nfi\nif [[ -z \"$BUNDLE_COMMAND\" ]]; then\n # Default Expo CLI command for bundling\n export BUNDLE_COMMAND=\"export:embed\"\nfi\n\n# Source .xcode.env.updates if it exists to allow\n# SKIP_BUNDLING to be unset if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.updates\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.updates\"\nfi\n# Source local changes to allow overrides\n# if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n\\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\`\n`;\n\n const expectedOutput = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n\nif [[ -z \"$CLI_PATH\" ]]; then\n # Use Expo CLI\n export CLI_PATH=\"$(\"$NODE_BINARY\" --print \"require.resolve('@expo/cli', { paths: [require.resolve('expo/package.json')] })\")\"\nfi\nif [[ -z \"$BUNDLE_COMMAND\" ]]; then\n # Default Expo CLI command for bundling\n export BUNDLE_COMMAND=\"export:embed\"\nfi\n\n# Source .xcode.env.updates if it exists to allow\n# SKIP_BUNDLING to be unset if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.updates\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.updates\"\nfi\n# Source local changes to allow overrides\n# if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n/bin/sh \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'\"\\` \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\`\n`;\n\n expect(addSentryWithBundledScriptsToBundleShellScript(input)).toBe(\n expectedOutput,\n );\n });\n\n it('if patching fails it does not add sentry cli to expo bundle build phase and shows code snippet', () => {\n const input = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n`;\n expect(addSentryWithBundledScriptsToBundleShellScript(input)).toEqual(\n new ErrorPatchSnippet(\n makeCodeSnippet(true, (unchanged, plus, _minus) => {\n return unchanged(\n `${plus(\n `/bin/sh \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'\"\\``,\n )} \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\``,\n );\n }),\n ),\n );\n expect(clack.log.error).toHaveBeenCalledWith(\n `Failed to patch ${chalk.cyan(\n 'Bundle React Native code and images',\n )} build phase.`,\n );\n });\n });\n\n describe('findBundlePhase', () => {\n it('returns build phase with react native xcode shell script', () => {\n const inputMap = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: 'bar',\n },\n 3: {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n },\n 4: {\n shellScript: 'qux',\n },\n };\n\n const expected = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n };\n\n expect(findBundlePhase(inputMap)).toEqual(expected);\n });\n\n it('returns undefined if bundle phase not present', () => {\n const inputMap = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: 'bar',\n },\n 3: {\n // note different path to the script\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/unknown/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n },\n 4: {\n shellScript: 'qux',\n },\n };\n\n expect(findBundlePhase(inputMap)).toBeUndefined();\n });\n });\n\n describe('doesBundlePhaseIncludeSentry', () => {\n it('returns true for script containing sentry cli calling react native xcode command', () => {\n const input = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\nSENTRY_CLI=\"sentry-cli react-native xcode\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$SENTRY_CLI $REACT_NATIVE_XCODE\\\"\"\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeTruthy();\n });\n\n it('returns true for script containing sentry bundled script', () => {\n const input = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\nSENTRY_CLI=\"sentry-cli react-native xcode\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\"\\\\\"\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeTruthy();\n });\n\n it('returns false', () => {\n const input = {\n // note sentry-cli can be part of the script but doesn't call react native xcode script\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\nsentry-cli --version\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeFalsy();\n });\n });\n\n describe('findDebugFilesUploadPhase', () => {\n it('returns debug files build phase using debug files command', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\nsentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\nsentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase with sentry-cli absolute path', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\n/path/to/bin/sentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\n/path/to/bin/sentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase using dsym command', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\nsentry-cli upload-dsym path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\nsentry-cli upload-dsym path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase using bundled scripts', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns undefined if build phase not present', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n // sentry-cli present but with different command\n shellScript: 'sentry-cli sourcempas upload',\n },\n };\n\n expect(findDebugFilesUploadPhase(input)).toBeUndefined();\n });\n });\n});\n"]}
|
|
1
|
+
{"version":3,"file":"xcode.test.js","sourceRoot":"","sources":["../../../test/react-native/xcode.test.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,sCAAsC;AACtC,mCAAyE;AACzE,wDAMsC;AACtC,kDAA0B;AAC1B,iDAAwD;AACxD,+EAA+E;AAC/E,sDAAwC;AAExC,WAAE,CAAC,IAAI,CAAC,gBAAgB,EAAE,KAAK,IAAI,EAAE,CAAC,CAAC;IACrC,UAAU,EAAE,IAAI;IAChB,GAAG,CAAC,MAAM,WAAE,CAAC,YAAY,CAAe,gBAAgB,CAAC,CAAC;CAC3D,CAAC,CAAC,CAAC;AAEJ,MAAM,mBAAmB,GAAG,QAAQ,CAAC;AACrC,MAAM,sBAAsB,GAAG,QAAQ,CAAC;AAExC,IAAA,iBAAQ,EAAC,oBAAoB,EAAE,GAAG,EAAE;IAClC,IAAA,mBAAU,EAAC,GAAG,EAAE;QACd,WAAE,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC,kBAAkB,CAAC,GAAG,EAAE;YACnD,WAAW;QACb,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,kBAAS,EAAC,GAAG,EAAE;QACb,WAAE,CAAC,aAAa,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,4CAA4C,EAAE,GAAG,EAAE;QAC1D,IAAA,WAAE,EAAC,0CAA0C,EAAE,GAAG,EAAE;YAClD,MAAM,KAAK,GAAG;;;;;mDAK+B,CAAC;YAC9C,uCAAuC;YACvC,yDAAyD;YACzD,sDAAsD;YACtD,MAAM,cAAc,GAAG;;;;;8HAKiG,CAAC;YAEzH,IAAA,eAAM,EACJ,IAAA,sDAA8C,EAC5C,KAAK,EACL,mBAAmB,CACpB,CACF,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,qGAAqG,EAAE,GAAG,EAAE;YAC7G,MAAM,KAAK,GAAG;;;;;mDAK+B,CAAC;YAC9C,MAAM,cAAc,GAAG;;;;;wHAK2F,CAAC;YAEnH,IAAA,eAAM,EACJ,IAAA,sDAA8C,EAC5C,KAAK,EACL,sBAAsB,CACvB,CACF,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,+GAA+G,EAAE,GAAG,EAAE;YACvH,MAAM,KAAK,GAAG;;;;;yDAKqC,CAAC;YAEpD,IAAA,eAAM,EACJ,IAAA,sDAA8C,EAC5C,KAAK,EACL,mBAAmB,CACpB,CACF,CAAC,OAAO,CACP,IAAI,yBAAiB,CACnB,IAAA,uBAAe,EAAC,IAAI,EAAE,CAAC,SAAS,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE;gBAChD,OAAO,SAAS,CAAC;;;gCAGG,IAAI,CACtB,0EAA0E,CAC3E,sBAAsB,IAAI,CAAC,KAAK,CAAC;CAC7C,CAAC,CAAC;YACO,CAAC,CAAC,CACH,CACF,CAAC;YACF,IAAA,eAAM,EAAC,KAAK,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,oBAAoB,CAC1C,mBAAmB,eAAK,CAAC,IAAI,CAC3B,qCAAqC,CACtC,eAAe,CACjB,CAAC;QACJ,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,4CAA4C,EAAE,GAAG,EAAE;YACpD,MAAM,KAAK,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAwCnB,CAAC;YAEI,MAAM,cAAc,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAwC5B,CAAC;YAEI,IAAA,eAAM,EACJ,IAAA,sDAA8C,EAC5C,KAAK,EACL,mBAAmB,CACpB,CACF,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,gGAAgG,EAAE,GAAG,EAAE;YACxG,MAAM,KAAK,GAAG;;;;;;;;;;;;;;;;;;CAkBnB,CAAC;YACI,IAAA,eAAM,EACJ,IAAA,sDAA8C,EAC5C,KAAK,EACL,mBAAmB,CACpB,CACF,CAAC,OAAO,CACP,IAAI,yBAAiB,CACnB,IAAA,uBAAe,EAAC,IAAI,EAAE,CAAC,SAAS,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE;gBAChD,OAAO,SAAS,CACd,GAAG,IAAI,CACL,iJAAiJ,CAClJ,wIAAwI,CAC1I,CAAC;YACJ,CAAC,CAAC,CACH,CACF,CAAC;YACF,IAAA,eAAM,EAAC,KAAK,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,oBAAoB,CAC1C,mBAAmB,eAAK,CAAC,IAAI,CAC3B,qCAAqC,CACtC,eAAe,CACjB,CAAC;QACJ,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,iBAAiB,EAAE,GAAG,EAAE;QAC/B,IAAA,WAAE,EAAC,0DAA0D,EAAE,GAAG,EAAE;YAClE,MAAM,QAAQ,GAAG;gBACf,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE;;;;;;CAMtB;iBACQ;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;aACF,CAAC;YAEF,MAAM,QAAQ,GAAG;gBACf,WAAW,EAAE;;;;;;CAMpB;aACM,CAAC;YAEF,IAAA,eAAM,EAAC,IAAA,uBAAe,EAAC,QAAQ,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QACtD,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,+CAA+C,EAAE,GAAG,EAAE;YACvD,MAAM,QAAQ,GAAG;gBACf,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,oCAAoC;oBACpC,WAAW,EAAE;;;;;;CAMtB;iBACQ;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;aACF,CAAC;YAEF,IAAA,eAAM,EAAC,IAAA,uBAAe,EAAC,QAAQ,CAAC,CAAC,CAAC,aAAa,EAAE,CAAC;QACpD,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,8BAA8B,EAAE,GAAG,EAAE;QAC5C,IAAA,WAAE,EAAC,kFAAkF,EAAE,GAAG,EAAE;YAC1F,MAAM,KAAK,GAAG;gBACZ,WAAW,EAAE;;;;;;CAMpB;aACM,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,oCAA4B,EAAC,KAAK,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC;QAC3D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,0DAA0D,EAAE,GAAG,EAAE;YAClE,MAAM,KAAK,GAAG;gBACZ,WAAW,EAAE;;;;;;CAMpB;aACM,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,oCAA4B,EAAC,KAAK,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC;QAC3D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,eAAe,EAAE,GAAG,EAAE;YACvB,MAAM,KAAK,GAAG;gBACZ,uFAAuF;gBACvF,WAAW,EAAE;;;;;;;CAOpB;aACM,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,oCAA4B,EAAC,KAAK,CAAC,CAAC,CAAC,SAAS,EAAE,CAAC;QAC1D,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,2BAA2B,EAAE,GAAG,EAAE;QACzC,IAAA,WAAE,EAAC,2DAA2D,EAAE,GAAG,EAAE;YACnE,MAAM,KAAK,GAAG;gBACZ,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,MAAM,QAAQ,GAAG;gBACf,GAAG;gBACH;oBACE,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,iCAAyB,EAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC7D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,+DAA+D,EAAE,GAAG,EAAE;YACvE,MAAM,KAAK,GAAG;gBACZ,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,MAAM,QAAQ,GAAG;gBACf,GAAG;gBACH;oBACE,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,iCAAyB,EAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC7D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,oDAAoD,EAAE,GAAG,EAAE;YAC5D,MAAM,KAAK,GAAG;gBACZ,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,MAAM,QAAQ,GAAG;gBACf,GAAG;gBACH;oBACE,WAAW,EAAE;;CAEtB;iBACQ;aACF,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,iCAAyB,EAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC7D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,uDAAuD,EAAE,GAAG,EAAE;YAC/D,MAAM,KAAK,GAAG;gBACZ,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,WAAW,EAAE,kFAAkF;iBAChG;aACF,CAAC;YACF,MAAM,QAAQ,GAAG;gBACf,GAAG;gBACH;oBACE,WAAW,EAAE,kFAAkF;iBAChG;aACF,CAAC;YACF,IAAA,eAAM,EAAC,IAAA,iCAAyB,EAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC7D,CAAC,CAAC,CAAC;QAEH,IAAA,WAAE,EAAC,8CAA8C,EAAE,GAAG,EAAE;YACtD,MAAM,KAAK,GAAG;gBACZ,CAAC,EAAE;oBACD,WAAW,EAAE,KAAK;iBACnB;gBACD,CAAC,EAAE;oBACD,gDAAgD;oBAChD,WAAW,EAAE,8BAA8B;iBAC5C;aACF,CAAC;YAEF,IAAA,eAAM,EAAC,IAAA,iCAAyB,EAAC,KAAK,CAAC,CAAC,CAAC,aAAa,EAAE,CAAC;QAC3D,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["/* eslint-disable no-useless-escape */\nimport { describe, expect, it, afterEach, beforeEach, vi } from 'vitest';\nimport {\n addSentryWithBundledScriptsToBundleShellScript,\n doesBundlePhaseIncludeSentry,\n findBundlePhase,\n findDebugFilesUploadPhase,\n ErrorPatchSnippet,\n} from '../../src/react-native/xcode';\nimport chalk from 'chalk';\nimport { makeCodeSnippet } from '../../src/utils/clack';\n// @ts-expect-error - clack is ESM and TS complains about that. It works though\nimport * as clack from '@clack/prompts';\n\nvi.mock('@clack/prompts', async () => ({\n __esModule: true,\n ...(await vi.importActual<typeof clack>('@clack/prompts')),\n}));\n\nconst rnVersionWithQuotes = '0.81.0';\nconst rnVersionWithoutQuotes = '0.81.1';\n\ndescribe('react-native xcode', () => {\n beforeEach(() => {\n vi.spyOn(clack.log, 'error').mockImplementation(() => {\n /* empty */\n });\n });\n\n afterEach(() => {\n vi.clearAllMocks();\n });\n\n describe('addSentryBundledScriptsToBundleShellScript', () => {\n it('adds sentry cli to rn bundle build phase', () => {\n const input = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT $REACT_NATIVE_XCODE\"`;\n // actual shell script looks like this:\n // /bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n // but during parsing xcode library removes the quotes\n const expectedOutput = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\\\\\"\"`;\n\n expect(\n addSentryWithBundledScriptsToBundleShellScript(\n input,\n rnVersionWithQuotes,\n ),\n ).toBe(expectedOutput);\n });\n\n it('does not add with-environment.sh parameter quotes for RN version >= 0.81.1 to rn bundle build phase', () => {\n const input = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT $REACT_NATIVE_XCODE\"`;\n const expectedOutput = `set -e\n\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT /bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\"`;\n\n expect(\n addSentryWithBundledScriptsToBundleShellScript(\n input,\n rnVersionWithoutQuotes,\n ),\n ).toBe(expectedOutput);\n });\n\n it('does not add sentry cli to rn bundle build phase if $REACT_NATIVE_XCODE is not present and shows code snippet', () => {\n const input = `set -e\n \n WITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\n REACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n \n /bin/sh -c \"$WITH_ENVIRONMENT $NOT_REACT_NATIVE_XCODE\"`;\n\n expect(\n addSentryWithBundledScriptsToBundleShellScript(\n input,\n rnVersionWithQuotes,\n ),\n ).toEqual(\n new ErrorPatchSnippet(\n makeCodeSnippet(true, (unchanged, plus, _minus) => {\n return unchanged(`WITH_ENVIRONMENT=\"$REACT_NATIVE_PATH/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"$REACT_NATIVE_PATH/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT ${plus(\n `\\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh `,\n )}$REACT_NATIVE_XCODE${plus(`\\\\\"`)}\"\n`);\n }),\n ),\n );\n expect(clack.log.error).toHaveBeenCalledWith(\n `Failed to patch ${chalk.cyan(\n 'Bundle React Native code and images',\n )} build phase.`,\n );\n });\n\n it('adds sentry cli to expo bundle build phase', () => {\n const input = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n\nif [[ -z \"$CLI_PATH\" ]]; then\n # Use Expo CLI\n export CLI_PATH=\"$(\"$NODE_BINARY\" --print \"require.resolve('@expo/cli', { paths: [require.resolve('expo/package.json')] })\")\"\nfi\nif [[ -z \"$BUNDLE_COMMAND\" ]]; then\n # Default Expo CLI command for bundling\n export BUNDLE_COMMAND=\"export:embed\"\nfi\n\n# Source .xcode.env.updates if it exists to allow\n# SKIP_BUNDLING to be unset if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.updates\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.updates\"\nfi\n# Source local changes to allow overrides\n# if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n\\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\`\n`;\n\n const expectedOutput = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n\nif [[ -z \"$CLI_PATH\" ]]; then\n # Use Expo CLI\n export CLI_PATH=\"$(\"$NODE_BINARY\" --print \"require.resolve('@expo/cli', { paths: [require.resolve('expo/package.json')] })\")\"\nfi\nif [[ -z \"$BUNDLE_COMMAND\" ]]; then\n # Default Expo CLI command for bundling\n export BUNDLE_COMMAND=\"export:embed\"\nfi\n\n# Source .xcode.env.updates if it exists to allow\n# SKIP_BUNDLING to be unset if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.updates\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.updates\"\nfi\n# Source local changes to allow overrides\n# if needed\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n/bin/sh \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'\"\\` \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\`\n`;\n\n expect(\n addSentryWithBundledScriptsToBundleShellScript(\n input,\n rnVersionWithQuotes,\n ),\n ).toBe(expectedOutput);\n });\n\n it('if patching fails it does not add sentry cli to expo bundle build phase and shows code snippet', () => {\n const input = `\nif [[ -f \"$PODS_ROOT/../.xcode.env\" ]]; then\n source \"$PODS_ROOT/../.xcode.env\"\nfi\nif [[ -f \"$PODS_ROOT/../.xcode.env.local\" ]]; then\n source \"$PODS_ROOT/../.xcode.env.local\"\nfi\n\n# The project root by default is one level up from the ios directory\nexport PROJECT_ROOT=\"$PROJECT_DIR\"/..\n\nif [[ \"$CONFIGURATION\" = *Debug* ]]; then\n export SKIP_BUNDLING=1\nfi\nif [[ -z \"$ENTRY_FILE\" ]]; then\n # Set the entry JS file using the bundler's entry resolution.\n export ENTRY_FILE=\"$(\"$NODE_BINARY\" -e \"require('expo/scripts/resolveAppEntry')\" \"$PROJECT_ROOT\" ios absolute | tail -n 1)\"\nfi\n`;\n expect(\n addSentryWithBundledScriptsToBundleShellScript(\n input,\n rnVersionWithQuotes,\n ),\n ).toEqual(\n new ErrorPatchSnippet(\n makeCodeSnippet(true, (unchanged, plus, _minus) => {\n return unchanged(\n `${plus(\n `/bin/sh \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('@sentry/react-native/package.json')) + '/scripts/sentry-xcode.sh'\"\\``,\n )} \\`\"$NODE_BINARY\" --print \"require('path').dirname(require.resolve('react-native/package.json')) + '/scripts/react-native-xcode.sh'\"\\``,\n );\n }),\n ),\n );\n expect(clack.log.error).toHaveBeenCalledWith(\n `Failed to patch ${chalk.cyan(\n 'Bundle React Native code and images',\n )} build phase.`,\n );\n });\n });\n\n describe('findBundlePhase', () => {\n it('returns build phase with react native xcode shell script', () => {\n const inputMap = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: 'bar',\n },\n 3: {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n },\n 4: {\n shellScript: 'qux',\n },\n };\n\n const expected = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n };\n\n expect(findBundlePhase(inputMap)).toEqual(expected);\n });\n\n it('returns undefined if bundle phase not present', () => {\n const inputMap = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: 'bar',\n },\n 3: {\n // note different path to the script\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/unknown/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\n`,\n },\n 4: {\n shellScript: 'qux',\n },\n };\n\n expect(findBundlePhase(inputMap)).toBeUndefined();\n });\n });\n\n describe('doesBundlePhaseIncludeSentry', () => {\n it('returns true for script containing sentry cli calling react native xcode command', () => {\n const input = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\nSENTRY_CLI=\"sentry-cli react-native xcode\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$SENTRY_CLI $REACT_NATIVE_XCODE\\\"\"\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeTruthy();\n });\n\n it('returns true for script containing sentry bundled script', () => {\n const input = {\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\nSENTRY_CLI=\"sentry-cli react-native xcode\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\\\"/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode.sh $REACT_NATIVE_XCODE\"\\\\\"\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeTruthy();\n });\n\n it('returns false', () => {\n const input = {\n // note sentry-cli can be part of the script but doesn't call react native xcode script\n shellScript: `set -e\nWITH_ENVIRONMENT=\"../node_modules/react-native/scripts/xcode/with-environment.sh\"\nREACT_NATIVE_XCODE=\"../node_modules/react-native/scripts/react-native-xcode.sh\"\n\n/bin/sh -c \"$WITH_ENVIRONMENT \\\"$REACT_NATIVE_XCODE\\\"\"\n\nsentry-cli --version\n`,\n };\n expect(doesBundlePhaseIncludeSentry(input)).toBeFalsy();\n });\n });\n\n describe('findDebugFilesUploadPhase', () => {\n it('returns debug files build phase using debug files command', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\nsentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\nsentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase with sentry-cli absolute path', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\n/path/to/bin/sentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\n/path/to/bin/sentry-cli debug-files upload path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase using dsym command', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `set -e\nsentry-cli upload-dsym path/to/dsym --include-sources\n`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `set -e\nsentry-cli upload-dsym path/to/dsym --include-sources\n`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns debug files build phase using bundled scripts', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n shellScript: `/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`,\n },\n };\n const expected = [\n '2',\n {\n shellScript: `/bin/sh ../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`,\n },\n ];\n expect(findDebugFilesUploadPhase(input)).toEqual(expected);\n });\n\n it('returns undefined if build phase not present', () => {\n const input = {\n 1: {\n shellScript: 'foo',\n },\n 2: {\n // sentry-cli present but with different command\n shellScript: 'sentry-cli sourcempas upload',\n },\n };\n\n expect(findDebugFilesUploadPhase(input)).toBeUndefined();\n });\n });\n});\n"]}
|
package/package.json
CHANGED