@sentry/wizard 4.7.0 → 4.9.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.
Files changed (175) hide show
  1. package/CHANGELOG.md +19 -0
  2. package/README.md +19 -19
  3. package/dist/e2e-tests/tests/angular-17.test.d.ts +1 -0
  4. package/dist/e2e-tests/tests/angular-17.test.js +196 -0
  5. package/dist/e2e-tests/tests/angular-17.test.js.map +1 -0
  6. package/dist/e2e-tests/tests/angular-19.test.d.ts +1 -0
  7. package/dist/e2e-tests/tests/angular-19.test.js +194 -0
  8. package/dist/e2e-tests/tests/angular-19.test.js.map +1 -0
  9. package/dist/e2e-tests/tests/expo.test.d.ts +1 -0
  10. package/dist/e2e-tests/tests/expo.test.js +103 -0
  11. package/dist/e2e-tests/tests/expo.test.js.map +1 -0
  12. package/dist/e2e-tests/tests/help-message.test.js +2 -2
  13. package/dist/e2e-tests/tests/help-message.test.js.map +1 -1
  14. package/dist/e2e-tests/tests/react-native.test.d.ts +1 -0
  15. package/dist/e2e-tests/tests/react-native.test.js +132 -0
  16. package/dist/e2e-tests/tests/react-native.test.js.map +1 -0
  17. package/dist/e2e-tests/tests/remix.test.js +4 -4
  18. package/dist/e2e-tests/tests/remix.test.js.map +1 -1
  19. package/dist/e2e-tests/tests/sveltekit.test.js +2 -2
  20. package/dist/e2e-tests/tests/sveltekit.test.js.map +1 -1
  21. package/dist/e2e-tests/utils/index.d.ts +7 -0
  22. package/dist/e2e-tests/utils/index.js +32 -7
  23. package/dist/e2e-tests/utils/index.js.map +1 -1
  24. package/dist/lib/Constants.d.ts +1 -0
  25. package/dist/lib/Constants.js +3 -0
  26. package/dist/lib/Constants.js.map +1 -1
  27. package/dist/lib/Helper/SentryCli.d.ts +0 -11
  28. package/dist/lib/Helper/SentryCli.js +0 -52
  29. package/dist/lib/Helper/SentryCli.js.map +1 -1
  30. package/dist/src/android/templates.js +2 -0
  31. package/dist/src/android/templates.js.map +1 -1
  32. package/dist/src/angular/angular-wizard.d.ts +3 -0
  33. package/dist/src/angular/angular-wizard.js +186 -0
  34. package/dist/src/angular/angular-wizard.js.map +1 -0
  35. package/dist/src/angular/codemods/app-config.d.ts +3 -0
  36. package/dist/src/angular/codemods/app-config.js +211 -0
  37. package/dist/src/angular/codemods/app-config.js.map +1 -0
  38. package/dist/src/angular/codemods/main.d.ts +20 -0
  39. package/dist/src/angular/codemods/main.js +62 -0
  40. package/dist/src/angular/codemods/main.js.map +1 -0
  41. package/dist/src/angular/codemods/sourcemaps.d.ts +21 -0
  42. package/dist/src/angular/codemods/sourcemaps.js +94 -0
  43. package/dist/src/angular/codemods/sourcemaps.js.map +1 -0
  44. package/dist/src/angular/example-component.d.ts +8 -0
  45. package/dist/src/angular/example-component.js +286 -0
  46. package/dist/src/angular/example-component.js.map +1 -0
  47. package/dist/src/angular/sdk-setup.d.ts +6 -0
  48. package/dist/src/angular/sdk-setup.js +99 -0
  49. package/dist/src/angular/sdk-setup.js.map +1 -0
  50. package/dist/src/apple/code-tools.d.ts +4 -2
  51. package/dist/src/apple/code-tools.js +21 -11
  52. package/dist/src/apple/code-tools.js.map +1 -1
  53. package/dist/src/apple/inject-code-snippet.js +5 -3
  54. package/dist/src/apple/inject-code-snippet.js.map +1 -1
  55. package/dist/src/apple/macos-system-helper.d.ts +5 -0
  56. package/dist/src/apple/macos-system-helper.js +86 -0
  57. package/dist/src/apple/macos-system-helper.js.map +1 -0
  58. package/dist/src/apple/templates.js +10 -0
  59. package/dist/src/apple/templates.js.map +1 -1
  60. package/dist/src/apple/xcode-manager.d.ts +237 -11
  61. package/dist/src/apple/xcode-manager.js +736 -65
  62. package/dist/src/apple/xcode-manager.js.map +1 -1
  63. package/dist/src/apple/xcode-project-object-with-id.d.ts +5 -0
  64. package/dist/src/apple/xcode-project-object-with-id.js +3 -0
  65. package/dist/src/apple/xcode-project-object-with-id.js.map +1 -0
  66. package/dist/src/flutter/flutter-wizard.js +10 -2
  67. package/dist/src/flutter/flutter-wizard.js.map +1 -1
  68. package/dist/src/flutter/templates.js +7 -1
  69. package/dist/src/flutter/templates.js.map +1 -1
  70. package/dist/src/nextjs/nextjs-wizard.js +27 -15
  71. package/dist/src/nextjs/nextjs-wizard.js.map +1 -1
  72. package/dist/src/nextjs/templates.js +56 -7
  73. package/dist/src/nextjs/templates.js.map +1 -1
  74. package/dist/src/nuxt/nuxt-wizard.js +1 -3
  75. package/dist/src/nuxt/nuxt-wizard.js.map +1 -1
  76. package/dist/src/nuxt/templates.js +30 -0
  77. package/dist/src/nuxt/templates.js.map +1 -1
  78. package/dist/src/react-native/expo-env-file.js +5 -0
  79. package/dist/src/react-native/expo-env-file.js.map +1 -1
  80. package/dist/src/react-native/expo-metro.js +22 -6
  81. package/dist/src/react-native/expo-metro.js.map +1 -1
  82. package/dist/src/react-native/expo.js +11 -1
  83. package/dist/src/react-native/expo.js.map +1 -1
  84. package/dist/src/react-native/glob.js +14 -4
  85. package/dist/src/react-native/glob.js.map +1 -1
  86. package/dist/src/react-native/gradle.js +14 -4
  87. package/dist/src/react-native/gradle.js.map +1 -1
  88. package/dist/src/react-native/javascript.d.ts +9 -4
  89. package/dist/src/react-native/javascript.js +52 -23
  90. package/dist/src/react-native/javascript.js.map +1 -1
  91. package/dist/src/react-native/metro.d.ts +1 -1
  92. package/dist/src/react-native/metro.js +36 -4
  93. package/dist/src/react-native/metro.js.map +1 -1
  94. package/dist/src/react-native/react-native-wizard.d.ts +4 -0
  95. package/dist/src/react-native/react-native-wizard.js +32 -4
  96. package/dist/src/react-native/react-native-wizard.js.map +1 -1
  97. package/dist/src/react-native/xcode.js +29 -10
  98. package/dist/src/react-native/xcode.js.map +1 -1
  99. package/dist/src/remix/remix-wizard.js +1 -3
  100. package/dist/src/remix/remix-wizard.js.map +1 -1
  101. package/dist/src/remix/sdk-example.js +30 -1
  102. package/dist/src/remix/sdk-example.js.map +1 -1
  103. package/dist/src/remix/sdk-setup.js +11 -5
  104. package/dist/src/remix/sdk-setup.js.map +1 -1
  105. package/dist/src/run.d.ts +1 -1
  106. package/dist/src/run.js +5 -0
  107. package/dist/src/run.js.map +1 -1
  108. package/dist/src/sourcemaps/sourcemaps-wizard.d.ts +1 -1
  109. package/dist/src/sourcemaps/sourcemaps-wizard.js +35 -20
  110. package/dist/src/sourcemaps/sourcemaps-wizard.js.map +1 -1
  111. package/dist/src/sourcemaps/tools/angular.d.ts +1 -0
  112. package/dist/src/sourcemaps/tools/angular.js +7 -7
  113. package/dist/src/sourcemaps/tools/angular.js.map +1 -1
  114. package/dist/src/sourcemaps/tools/sentry-cli.d.ts +5 -1
  115. package/dist/src/sourcemaps/tools/sentry-cli.js +6 -3
  116. package/dist/src/sourcemaps/tools/sentry-cli.js.map +1 -1
  117. package/dist/src/sourcemaps/tools/tsc.js +5 -1
  118. package/dist/src/sourcemaps/tools/tsc.js.map +1 -1
  119. package/dist/src/sourcemaps/tools/vite.js +4 -1
  120. package/dist/src/sourcemaps/tools/vite.js.map +1 -1
  121. package/dist/src/sourcemaps/tools/webpack.js +4 -1
  122. package/dist/src/sourcemaps/tools/webpack.js.map +1 -1
  123. package/dist/src/sveltekit/sdk-example.js +1 -1
  124. package/dist/src/sveltekit/sdk-example.js.map +1 -1
  125. package/dist/src/sveltekit/sveltekit-wizard.js +3 -5
  126. package/dist/src/sveltekit/sveltekit-wizard.js.map +1 -1
  127. package/dist/src/sveltekit/templates.js +28 -1
  128. package/dist/src/sveltekit/templates.js.map +1 -1
  129. package/dist/src/utils/clack/index.d.ts +13 -15
  130. package/dist/src/utils/clack/index.js +17 -50
  131. package/dist/src/utils/clack/index.js.map +1 -1
  132. package/dist/src/utils/git.d.ts +11 -0
  133. package/dist/src/utils/git.js +69 -0
  134. package/dist/src/utils/git.js.map +1 -0
  135. package/dist/src/utils/sentrycli-utils.js +13 -4
  136. package/dist/src/utils/sentrycli-utils.js.map +1 -1
  137. package/dist/src/version.d.ts +1 -1
  138. package/dist/src/version.js +1 -1
  139. package/dist/src/version.js.map +1 -1
  140. package/dist/test/angular/angular-wizard.test.d.ts +1 -0
  141. package/dist/test/angular/angular-wizard.test.js +27 -0
  142. package/dist/test/angular/angular-wizard.test.js.map +1 -0
  143. package/dist/test/angular/codemods/sourcemaps.test.d.ts +1 -0
  144. package/dist/test/angular/codemods/sourcemaps.test.js +237 -0
  145. package/dist/test/angular/codemods/sourcemaps.test.js.map +1 -0
  146. package/dist/test/angular/example-component.test.d.ts +1 -0
  147. package/dist/test/angular/example-component.test.js +105 -0
  148. package/dist/test/angular/example-component.test.js.map +1 -0
  149. package/dist/test/apple/code-tools.test.js +54 -35
  150. package/dist/test/apple/code-tools.test.js.map +1 -1
  151. package/dist/test/apple/configure-sentry-cli.test.d.ts +1 -0
  152. package/dist/test/apple/configure-sentry-cli.test.js +131 -0
  153. package/dist/test/apple/configure-sentry-cli.test.js.map +1 -0
  154. package/dist/test/apple/macos-system-helper-mocked.test.d.ts +1 -0
  155. package/dist/test/apple/macos-system-helper-mocked.test.js +46 -0
  156. package/dist/test/apple/macos-system-helper-mocked.test.js.map +1 -0
  157. package/dist/test/apple/macos-system-helper.test.d.ts +1 -0
  158. package/dist/test/apple/macos-system-helper.test.js +88 -0
  159. package/dist/test/apple/macos-system-helper.test.js.map +1 -0
  160. package/dist/test/apple/templates.test.js +10 -0
  161. package/dist/test/apple/templates.test.js.map +1 -1
  162. package/dist/test/apple/xcode-manager.test.js +745 -379
  163. package/dist/test/apple/xcode-manager.test.js.map +1 -1
  164. package/dist/test/flutter/templates.test.js +9 -0
  165. package/dist/test/flutter/templates.test.js.map +1 -1
  166. package/dist/test/react-native/javascript.test.js +119 -0
  167. package/dist/test/react-native/javascript.test.js.map +1 -1
  168. package/dist/test/react-native/metro.test.js +113 -0
  169. package/dist/test/react-native/metro.test.js.map +1 -1
  170. package/dist/test/remix/client-entry.test.js +10 -10
  171. package/dist/test/remix/client-entry.test.js.map +1 -1
  172. package/dist/test/utils/git.test.d.ts +1 -0
  173. package/dist/test/utils/git.test.js +70 -0
  174. package/dist/test/utils/git.test.js.map +1 -0
  175. package/package.json +1 -1
@@ -0,0 +1,103 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ Object.defineProperty(exports, "__esModule", { value: true });
26
+ const path = __importStar(require("node:path"));
27
+ const Constants_1 = require("../../lib/Constants");
28
+ const utils_1 = require("../utils");
29
+ const utils_2 = require("../utils");
30
+ const utils_3 = require("../utils");
31
+ const vitest_1 = require("vitest");
32
+ (0, vitest_1.describe)('Expo', () => {
33
+ const integration = Constants_1.Integration.reactNative;
34
+ const projectDir = path.resolve(__dirname, '../test-applications/react-native-expo-test-app');
35
+ (0, vitest_1.beforeAll)(async () => {
36
+ const wizardInstance = (0, utils_2.startWizardInstance)(integration, projectDir);
37
+ const packageManagerPrompted = await wizardInstance.waitForOutput('Please select your package manager.');
38
+ const sessionReplayPrompted = packageManagerPrompted &&
39
+ (await wizardInstance.sendStdinAndWaitForOutput(
40
+ // Selecting `yarn` as the package manager
41
+ [utils_1.KEYS.DOWN, utils_1.KEYS.DOWN, utils_1.KEYS.ENTER], 'Do you want to enable Session Replay to help debug issues? (See https://docs.sentry.io/platforms/react-native/session-replay/)'));
42
+ const feedbackWidgetPrompted = sessionReplayPrompted &&
43
+ (await wizardInstance.sendStdinAndWaitForOutput(
44
+ // Enable session replay
45
+ [utils_1.KEYS.ENTER], 'Do you want to enable the Feedback Widget to collect feedback from your users? (See https://docs.sentry.io/platforms/react-native/user-feedback/)'));
46
+ const testEventPrompted = feedbackWidgetPrompted &&
47
+ (await wizardInstance.sendStdinAndWaitForOutput(
48
+ // Enable feedback widget
49
+ [utils_1.KEYS.ENTER], 'Have you successfully sent a test event?'));
50
+ testEventPrompted &&
51
+ (await wizardInstance.sendStdinAndWaitForOutput(
52
+ // Respond that test event was sent
53
+ [utils_1.KEYS.ENTER], 'Everything is set up!'));
54
+ wizardInstance.kill();
55
+ });
56
+ (0, vitest_1.afterAll)(() => {
57
+ (0, utils_1.revertLocalChanges)(projectDir);
58
+ (0, utils_1.cleanupGit)(projectDir);
59
+ });
60
+ (0, vitest_1.test)('package.json is updated correctly', () => {
61
+ (0, utils_3.checkFileContents)(`${projectDir}/package.json`, `@sentry/react-native`);
62
+ });
63
+ (0, vitest_1.test)('_layout.tsx is updated correctly', () => {
64
+ (0, utils_3.checkFileContents)(`${projectDir}/app/_layout.tsx`, `import * as Sentry from '@sentry/react-native';
65
+
66
+ Sentry.init({
67
+ dsn: 'https://public@dsn.ingest.sentry.io/1337',
68
+
69
+ // Adds more context data to events (IP address, cookies, user, etc.)
70
+ // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/
71
+ sendDefaultPii: true,
72
+
73
+ // Configure Session Replay
74
+ replaysSessionSampleRate: 0.1,
75
+ replaysOnErrorSampleRate: 1,
76
+ integrations: [Sentry.mobileReplayIntegration(), Sentry.feedbackIntegration()],
77
+
78
+ // uncomment the line below to enable Spotlight (https://spotlightjs.com)
79
+ // spotlight: __DEV__,
80
+ });`);
81
+ (0, utils_3.checkFileContents)(`${projectDir}/app/_layout.tsx`, `export default Sentry.wrap(function RootLayout() {`);
82
+ });
83
+ (0, vitest_1.test)('app.json is updated correctly', () => {
84
+ (0, utils_3.checkFileContents)(`${projectDir}/app.json`, `"@sentry/react-native/expo",
85
+ {
86
+ "url": "https://sentry.io/",
87
+ "project": "${utils_1.TEST_ARGS.PROJECT_SLUG}",
88
+ "organization": "${utils_1.TEST_ARGS.ORG_SLUG}"
89
+ }`);
90
+ });
91
+ (0, vitest_1.test)('metro.config.js is added', () => {
92
+ (0, utils_1.checkFileExists)(`${projectDir}/metro.config.js`);
93
+ (0, utils_3.checkFileContents)(`${projectDir}/metro.config.js`, `const { getSentryExpoConfig } = require("@sentry/react-native/metro");
94
+
95
+ const config = getSentryExpoConfig(__dirname);
96
+
97
+ module.exports = config;`);
98
+ });
99
+ (0, vitest_1.test)('.gitignore is updated correctly', () => {
100
+ (0, utils_3.checkFileContents)(`${projectDir}/.gitignore`, `.env.local`);
101
+ });
102
+ });
103
+ //# sourceMappingURL=expo.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"expo.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/expo.test.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AAAA,gDAAkC;AAClC,mDAAkD;AAClD,oCAMkB;AAClB,oCAA+C;AAC/C,oCAA6C;AAC7C,mCAA6D;AAE7D,IAAA,iBAAQ,EAAC,MAAM,EAAE,GAAG,EAAE;IACpB,MAAM,WAAW,GAAG,uBAAW,CAAC,WAAW,CAAC;IAC5C,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,CAC7B,SAAS,EACT,iDAAiD,CAClD,CAAC;IAEF,IAAA,kBAAS,EAAC,KAAK,IAAI,EAAE;QACnB,MAAM,cAAc,GAAG,IAAA,2BAAmB,EAAC,WAAW,EAAE,UAAU,CAAC,CAAC;QACpE,MAAM,sBAAsB,GAAG,MAAM,cAAc,CAAC,aAAa,CAC/D,qCAAqC,CACtC,CAAC;QACF,MAAM,qBAAqB,GAC3B,sBAAsB;YACtB,CAAC,MAAM,cAAc,CAAC,yBAAyB;YAC7C,0CAA0C;YAC1C,CAAC,YAAI,CAAC,IAAI,EAAE,YAAI,CAAC,IAAI,EAAE,YAAI,CAAC,KAAK,CAAC,EAClC,gIAAgI,CACjI,CAAC,CAAC;QACH,MAAM,sBAAsB,GAC5B,qBAAqB;YACnB,CAAC,MAAM,cAAc,CAAC,yBAAyB;YAC7C,wBAAwB;YACxB,CAAC,YAAI,CAAC,KAAK,CAAC,EACZ,mJAAmJ,CACpJ,CAAC,CAAC;QACL,MAAM,iBAAiB,GACvB,sBAAsB;YACpB,CAAC,MAAM,cAAc,CAAC,yBAAyB;YAC7C,yBAAyB;YACzB,CAAC,YAAI,CAAC,KAAK,CAAC,EACZ,0CAA0C,CAC3C,CAAC,CAAC;QACL,iBAAiB;YACf,CAAC,MAAM,cAAc,CAAC,yBAAyB;YAC7C,mCAAmC;YACnC,CAAC,YAAI,CAAC,KAAK,CAAC,EACZ,uBAAuB,CACxB,CAAC,CAAC;QACL,cAAc,CAAC,IAAI,EAAE,CAAC;IACxB,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,GAAG,EAAE;QACZ,IAAA,0BAAkB,EAAC,UAAU,CAAC,CAAC;QAC/B,IAAA,kBAAU,EAAC,UAAU,CAAC,CAAC;IACzB,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,mCAAmC,EAAE,GAAG,EAAE;QAC7C,IAAA,yBAAiB,EAAC,GAAG,UAAU,eAAe,EAAE,sBAAsB,CAAC,CAAC;IAC1E,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,kCAAkC,EAAE,GAAG,EAAE;QAC5C,IAAA,yBAAiB,EACf,GAAG,UAAU,kBAAkB,EAC/B;;;;;;;;;;;;;;;;IAgBF,CACC,CAAC;QACF,IAAA,yBAAiB,EACf,GAAG,UAAU,kBAAkB,EAC/B,oDAAoD,CACrD,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,+BAA+B,EAAE,GAAG,EAAE;QACzC,IAAA,yBAAiB,EACf,GAAG,UAAU,WAAW,EACxB;;;wBAGkB,iBAAS,CAAC,YAAY;6BACjB,iBAAS,CAAC,QAAQ;UACrC,CACL,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,0BAA0B,EAAE,GAAG,EAAE;QACpC,IAAA,uBAAe,EAAC,GAAG,UAAU,kBAAkB,CAAC,CAAC;QACjD,IAAA,yBAAiB,EACf,GAAG,UAAU,kBAAkB,EAC/B;;;;yBAImB,CACpB,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,iCAAiC,EAAE,GAAG,EAAE;QAC3C,IAAA,yBAAiB,EAAC,GAAG,UAAU,aAAa,EAAE,YAAY,CAAC,CAAC;IAC9D,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport {\n KEYS,\n TEST_ARGS,\n checkFileExists,\n cleanupGit,\n revertLocalChanges,\n} from '../utils';\nimport { startWizardInstance } from '../utils';\nimport { checkFileContents } from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\ndescribe('Expo', () => {\n const integration = Integration.reactNative;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/react-native-expo-test-app',\n );\n\n beforeAll(async () => {\n const wizardInstance = startWizardInstance(integration, projectDir);\n const packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager.',\n );\n const sessionReplayPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.DOWN, KEYS.ENTER],\n 'Do you want to enable Session Replay to help debug issues? (See https://docs.sentry.io/platforms/react-native/session-replay/)',\n ));\n const feedbackWidgetPrompted =\n sessionReplayPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Enable session replay\n [KEYS.ENTER],\n 'Do you want to enable the Feedback Widget to collect feedback from your users? (See https://docs.sentry.io/platforms/react-native/user-feedback/)',\n ));\n const testEventPrompted =\n feedbackWidgetPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Enable feedback widget\n [KEYS.ENTER],\n 'Have you successfully sent a test event?',\n ));\n testEventPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Respond that test event was sent\n [KEYS.ENTER],\n 'Everything is set up!',\n ));\n wizardInstance.kill();\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n test('package.json is updated correctly', () => {\n checkFileContents(`${projectDir}/package.json`, `@sentry/react-native`);\n });\n\n test('_layout.tsx is updated correctly', () => {\n checkFileContents(\n `${projectDir}/app/_layout.tsx`,\n `import * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://public@dsn.ingest.sentry.io/1337',\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 );\n checkFileContents(\n `${projectDir}/app/_layout.tsx`,\n `export default Sentry.wrap(function RootLayout() {`,\n );\n });\n\n test('app.json is updated correctly', () => {\n checkFileContents(\n `${projectDir}/app.json`,\n `\"@sentry/react-native/expo\",\n {\n \"url\": \"https://sentry.io/\",\n \"project\": \"${TEST_ARGS.PROJECT_SLUG}\",\n \"organization\": \"${TEST_ARGS.ORG_SLUG}\"\n }`,\n );\n });\n\n test('metro.config.js is added', () => {\n checkFileExists(`${projectDir}/metro.config.js`);\n checkFileContents(\n `${projectDir}/metro.config.js`,\n `const { getSentryExpoConfig } = require(\"@sentry/react-native/metro\");\n\nconst config = getSentryExpoConfig(__dirname);\n\nmodule.exports = config;`,\n );\n });\n\n test('.gitignore is updated correctly', () => {\n checkFileContents(`${projectDir}/.gitignore`, `.env.local`);\n });\n});\n"]}
@@ -27,8 +27,8 @@ const vitest_1 = require("vitest");
27
27
  env: SENTRY_WIZARD_QUIET [boolean] [default: false]
28
28
  -i, --integration Choose the integration to setup
29
29
  env: SENTRY_WIZARD_INTEGRATION
30
- [choices: "reactNative", "flutter", "ios", "android", "cordova", "electron",
31
- "nextjs", "nuxt", "remix", "sveltekit", "sourcemaps"]
30
+ [choices: "reactNative", "flutter", "ios", "android", "cordova", "angular",
31
+ "electron", "nextjs", "nuxt", "remix", "sveltekit", "sourcemaps"]
32
32
  -p, --platform Choose platform(s)
33
33
  env: SENTRY_WIZARD_PLATFORM
34
34
  [array] [choices: "ios", "android"]
@@ -1 +1 @@
1
- {"version":3,"file":"help-message.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/help-message.test.ts"],"names":[],"mappings":";;AAAA,2DAA8C;AAC9C,yCAAiC;AACjC,mCAA8C;AAE9C,IAAA,iBAAQ,EAAC,gBAAgB,EAAE,GAAG,EAAE;IAC9B,IAAA,WAAE,EAAC,oCAAoC,EAAE,GAAG,EAAE;QAC5C,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,0BAA0B;YACpD,CAAC,CAAC,CAAC,UAAU,EAAE,iBAAiB,OAAO,CAAC,QAAQ,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;YACnE,CAAC,CAAC,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;QAEvB,MAAM,OAAO,GAAG,IAAA,gBAAI,EAAC,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,OAAO,CAAC,CAAC;QAExD,MAAM,MAAM,GAAG,IAAA,6BAAQ,EAAC,GAAG,OAAO,SAAS,EAAE;YAC3C,KAAK,EAAE,MAAM;SACd,CAAC,CAAC;QAEH,IAAA,eAAM,EAAC,MAAM,CAAC,QAAQ,EAAE,CAAC,CAAC,qBAAqB,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAsC/C,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["import { execSync } from 'node:child_process';\nimport { join } from 'node:path';\nimport { describe, expect, it } from 'vitest';\n\ndescribe('--help command', () => {\n it('prints the up to date help command', () => {\n const binName = process.env.SENTRY_WIZARD_E2E_TEST_BIN\n ? ['dist-bin', `sentry-wizard-${process.platform}-${process.arch}`]\n : ['dist', 'bin.js'];\n\n const binPath = join(__dirname, '..', '..', ...binName);\n\n const output = execSync(`${binPath} --help`, {\n stdio: 'pipe',\n });\n\n expect(output.toString()).toMatchInlineSnapshot(`\n \"Options:\n --help Show help [boolean]\n --debug Enable verbose logging\n env: SENTRY_WIZARD_DEBUG [boolean] [default: false]\n --uninstall Revert project setup process\n env: SENTRY_WIZARD_UNINSTALL\n [boolean] [default: false]\n --skip-connect Skips the connection to the server\n env: SENTRY_WIZARD_SKIP_CONNECT\n [boolean] [default: false]\n --quiet Do not fallback to prompting user asking questions\n env: SENTRY_WIZARD_QUIET [boolean] [default: false]\n -i, --integration Choose the integration to setup\n env: SENTRY_WIZARD_INTEGRATION\n [choices: \"reactNative\", \"flutter\", \"ios\", \"android\", \"cordova\", \"electron\",\n \"nextjs\", \"nuxt\", \"remix\", \"sveltekit\", \"sourcemaps\"]\n -p, --platform Choose platform(s)\n env: SENTRY_WIZARD_PLATFORM\n [array] [choices: \"ios\", \"android\"]\n -u, --url The url to your Sentry installation\n env: SENTRY_WIZARD_URL\n --project The Sentry project slug to use\n [string] [default: Select project during setup]\n --org The Sentry org slug to use\n [string] [default: Select org during setup]\n --saas Skip the self-hosted or SaaS URL selection process\n [boolean] [default: Select self-hosted or SaaS during setup]\n -s, --signup Redirect to signup page if not logged in\n [boolean] [default: false]\n --disable-telemetry Don't send telemetry data to Sentry\n [boolean] [default: false]\n --force-install Force install the SDK NPM package\n [boolean] [default: false]\n --ignore-git-changes Ignore git changes in the project\n [boolean] [default: false]\n --version Show version number [boolean]\n \"\n `);\n });\n});\n"]}
1
+ {"version":3,"file":"help-message.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/help-message.test.ts"],"names":[],"mappings":";;AAAA,2DAA8C;AAC9C,yCAAiC;AACjC,mCAA8C;AAE9C,IAAA,iBAAQ,EAAC,gBAAgB,EAAE,GAAG,EAAE;IAC9B,IAAA,WAAE,EAAC,oCAAoC,EAAE,GAAG,EAAE;QAC5C,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,0BAA0B;YACpD,CAAC,CAAC,CAAC,UAAU,EAAE,iBAAiB,OAAO,CAAC,QAAQ,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;YACnE,CAAC,CAAC,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;QAEvB,MAAM,OAAO,GAAG,IAAA,gBAAI,EAAC,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,OAAO,CAAC,CAAC;QAExD,MAAM,MAAM,GAAG,IAAA,6BAAQ,EAAC,GAAG,OAAO,SAAS,EAAE;YAC3C,KAAK,EAAE,MAAM;SACd,CAAC,CAAC;QAEH,IAAA,eAAM,EAAC,MAAM,CAAC,QAAQ,EAAE,CAAC,CAAC,qBAAqB,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KAsC/C,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["import { execSync } from 'node:child_process';\nimport { join } from 'node:path';\nimport { describe, expect, it } from 'vitest';\n\ndescribe('--help command', () => {\n it('prints the up to date help command', () => {\n const binName = process.env.SENTRY_WIZARD_E2E_TEST_BIN\n ? ['dist-bin', `sentry-wizard-${process.platform}-${process.arch}`]\n : ['dist', 'bin.js'];\n\n const binPath = join(__dirname, '..', '..', ...binName);\n\n const output = execSync(`${binPath} --help`, {\n stdio: 'pipe',\n });\n\n expect(output.toString()).toMatchInlineSnapshot(`\n \"Options:\n --help Show help [boolean]\n --debug Enable verbose logging\n env: SENTRY_WIZARD_DEBUG [boolean] [default: false]\n --uninstall Revert project setup process\n env: SENTRY_WIZARD_UNINSTALL\n [boolean] [default: false]\n --skip-connect Skips the connection to the server\n env: SENTRY_WIZARD_SKIP_CONNECT\n [boolean] [default: false]\n --quiet Do not fallback to prompting user asking questions\n env: SENTRY_WIZARD_QUIET [boolean] [default: false]\n -i, --integration Choose the integration to setup\n env: SENTRY_WIZARD_INTEGRATION\n [choices: \"reactNative\", \"flutter\", \"ios\", \"android\", \"cordova\", \"angular\",\n \"electron\", \"nextjs\", \"nuxt\", \"remix\", \"sveltekit\", \"sourcemaps\"]\n -p, --platform Choose platform(s)\n env: SENTRY_WIZARD_PLATFORM\n [array] [choices: \"ios\", \"android\"]\n -u, --url The url to your Sentry installation\n env: SENTRY_WIZARD_URL\n --project The Sentry project slug to use\n [string] [default: Select project during setup]\n --org The Sentry org slug to use\n [string] [default: Select org during setup]\n --saas Skip the self-hosted or SaaS URL selection process\n [boolean] [default: Select self-hosted or SaaS during setup]\n -s, --signup Redirect to signup page if not logged in\n [boolean] [default: false]\n --disable-telemetry Don't send telemetry data to Sentry\n [boolean] [default: false]\n --force-install Force install the SDK NPM package\n [boolean] [default: false]\n --ignore-git-changes Ignore git changes in the project\n [boolean] [default: false]\n --version Show version number [boolean]\n \"\n `);\n });\n});\n"]}
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,132 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ Object.defineProperty(exports, "__esModule", { value: true });
26
+ const path = __importStar(require("node:path"));
27
+ const Constants_1 = require("../../lib/Constants");
28
+ const utils_1 = require("../utils");
29
+ const utils_2 = require("../utils");
30
+ const utils_3 = require("../utils");
31
+ const vitest_1 = require("vitest");
32
+ (0, vitest_1.describe)('ReactNative', () => {
33
+ const integration = Constants_1.Integration.reactNative;
34
+ const projectDir = path.resolve(__dirname, '../test-applications/react-native-test-app');
35
+ let podInstallPrompted = false;
36
+ (0, vitest_1.beforeAll)(async () => {
37
+ const wizardInstance = (0, utils_2.startWizardInstance)(integration, projectDir);
38
+ const packageManagerPrompted = await wizardInstance.waitForOutput('Please select your package manager.');
39
+ const sessionReplayPrompted = packageManagerPrompted &&
40
+ (await wizardInstance.sendStdinAndWaitForOutput(
41
+ // Selecting `yarn` as the package manager
42
+ [utils_1.KEYS.DOWN, utils_1.KEYS.DOWN, utils_1.KEYS.ENTER], 'Do you want to enable Session Replay to help debug issues? (See https://docs.sentry.io/platforms/react-native/session-replay/)'));
43
+ const feedbackWidgetPrompted = sessionReplayPrompted &&
44
+ (await wizardInstance.sendStdinAndWaitForOutput(
45
+ // Enable session replay
46
+ [utils_1.KEYS.ENTER], 'Do you want to enable the Feedback Widget to collect feedback from your users? (See https://docs.sentry.io/platforms/react-native/user-feedback/)'));
47
+ podInstallPrompted =
48
+ feedbackWidgetPrompted &&
49
+ (await wizardInstance.sendStdinAndWaitForOutput(
50
+ // Enable feedback widget
51
+ [utils_1.KEYS.ENTER], 'Do you want to run `pod install` now?', {
52
+ optional: true,
53
+ timeout: 5000,
54
+ }));
55
+ const prettierPrompted = podInstallPrompted &&
56
+ (await wizardInstance.sendStdinAndWaitForOutput(
57
+ // Skip pod install
58
+ [utils_1.KEYS.DOWN, utils_1.KEYS.ENTER], 'Looks like you have Prettier in your project. Do you want to run it on your files?'));
59
+ const testEventPrompted = prettierPrompted &&
60
+ (await wizardInstance.sendStdinAndWaitForOutput(
61
+ // Skip prettier
62
+ [utils_1.KEYS.DOWN, utils_1.KEYS.ENTER], 'Have you successfully sent a test event?'));
63
+ testEventPrompted &&
64
+ (await wizardInstance.sendStdinAndWaitForOutput(
65
+ // Respond that test event was sent
66
+ [utils_1.KEYS.ENTER], 'Everything is set up!'));
67
+ wizardInstance.kill();
68
+ });
69
+ (0, vitest_1.afterAll)(() => {
70
+ (0, utils_1.revertLocalChanges)(projectDir);
71
+ (0, utils_1.cleanupGit)(projectDir);
72
+ });
73
+ (0, vitest_1.test)('package.json is updated correctly', () => {
74
+ (0, utils_3.checkFileContents)(`${projectDir}/package.json`, `@sentry/react-native`);
75
+ });
76
+ (0, vitest_1.test)('metro.config.js is updated correctly', () => {
77
+ (0, utils_3.checkFileContents)(`${projectDir}/metro.config.js`, `const {
78
+ withSentryConfig
79
+ } = require("@sentry/react-native/metro");`);
80
+ (0, utils_3.checkFileContents)(`${projectDir}/metro.config.js`, `module.exports = withSentryConfig(mergeConfig(getDefaultConfig(__dirname), config));`);
81
+ });
82
+ (0, vitest_1.test)('App.tsx is updated correctly', () => {
83
+ (0, utils_3.checkFileContents)(`${projectDir}/App.tsx`, `import * as Sentry from '@sentry/react-native';
84
+
85
+ Sentry.init({
86
+ dsn: 'https://public@dsn.ingest.sentry.io/1337',
87
+
88
+ // Adds more context data to events (IP address, cookies, user, etc.)
89
+ // For more information, visit: https://docs.sentry.io/platforms/react-native/data-management/data-collected/
90
+ sendDefaultPii: true,
91
+
92
+ // Configure Session Replay
93
+ replaysSessionSampleRate: 0.1,
94
+ replaysOnErrorSampleRate: 1,
95
+ integrations: [Sentry.mobileReplayIntegration(), Sentry.feedbackIntegration()],
96
+
97
+ // uncomment the line below to enable Spotlight (https://spotlightjs.com)
98
+ // spotlight: __DEV__,
99
+ });`);
100
+ (0, utils_3.checkFileContents)(`${projectDir}/App.tsx`, `export default Sentry.wrap(App);`);
101
+ });
102
+ (0, vitest_1.test)('ios/sentry.properties is added', () => {
103
+ if (!podInstallPrompted) {
104
+ return;
105
+ }
106
+ (0, utils_3.checkFileContents)(`${projectDir}/ios/sentry.properties`, `auth.token=${utils_1.TEST_ARGS.AUTH_TOKEN}
107
+
108
+ defaults.org=${utils_1.TEST_ARGS.ORG_SLUG}
109
+ defaults.project=${utils_1.TEST_ARGS.PROJECT_SLUG}
110
+
111
+ defaults.url=https://sentry.io/`);
112
+ });
113
+ (0, vitest_1.test)('android/sentry.properties is added', () => {
114
+ (0, utils_3.checkFileContents)(`${projectDir}/android/sentry.properties`, `auth.token=${utils_1.TEST_ARGS.AUTH_TOKEN}
115
+
116
+ defaults.org=${utils_1.TEST_ARGS.ORG_SLUG}
117
+ defaults.project=${utils_1.TEST_ARGS.PROJECT_SLUG}
118
+
119
+ defaults.url=https://sentry.io/`);
120
+ });
121
+ (0, vitest_1.test)('build.gradle is updated correctly', () => {
122
+ (0, utils_3.checkFileContents)(`${projectDir}/android/app/build.gradle`, `apply from: new File(["node", "--print", "require.resolve('@sentry/react-native/package.json')"].execute().text.trim(), "../sentry.gradle")`);
123
+ });
124
+ (0, vitest_1.test)('xcode project is updated correctly', () => {
125
+ if (!podInstallPrompted) {
126
+ return;
127
+ }
128
+ (0, utils_3.checkFileContents)(`${projectDir}/ios/reactnative078.xcodeproj/project.pbxproj`, `../node_modules/@sentry/react-native/scripts/sentry-xcode.sh`);
129
+ (0, utils_3.checkFileContents)(`${projectDir}/ios/reactnative078.xcodeproj/project.pbxproj`, `../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`);
130
+ });
131
+ });
132
+ //# sourceMappingURL=react-native.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"react-native.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/react-native.test.ts"],"names":[],"mappings":"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","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport { KEYS, TEST_ARGS, cleanupGit, revertLocalChanges } from '../utils';\nimport { startWizardInstance } from '../utils';\nimport { checkFileContents } from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\ndescribe('ReactNative', () => {\n const integration = Integration.reactNative;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/react-native-test-app',\n );\n\n let podInstallPrompted = false;\n\n beforeAll(async () => {\n const wizardInstance = startWizardInstance(integration, projectDir);\n const packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager.',\n );\n const sessionReplayPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.DOWN, KEYS.ENTER],\n 'Do you want to enable Session Replay to help debug issues? (See https://docs.sentry.io/platforms/react-native/session-replay/)',\n ));\n\n const feedbackWidgetPrompted =\n sessionReplayPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Enable session replay\n [KEYS.ENTER],\n 'Do you want to enable the Feedback Widget to collect feedback from your users? (See https://docs.sentry.io/platforms/react-native/user-feedback/)',\n ));\n\n podInstallPrompted =\n feedbackWidgetPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Enable feedback widget\n [KEYS.ENTER],\n 'Do you want to run `pod install` now?',\n {\n optional: true,\n timeout: 5000,\n },\n ));\n\n const prettierPrompted =\n podInstallPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Skip pod install\n [KEYS.DOWN, KEYS.ENTER],\n 'Looks like you have Prettier in your project. Do you want to run it on your files?',\n ));\n\n const testEventPrompted =\n prettierPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Skip prettier\n [KEYS.DOWN, KEYS.ENTER],\n 'Have you successfully sent a test event?',\n ));\n \n testEventPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Respond that test event was sent\n [KEYS.ENTER],\n 'Everything is set up!',\n ));\n wizardInstance.kill();\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n test('package.json is updated correctly', () => {\n checkFileContents(`${projectDir}/package.json`, `@sentry/react-native`);\n });\n\n test('metro.config.js is updated correctly', () => {\n checkFileContents(\n `${projectDir}/metro.config.js`,\n `const {\n withSentryConfig\n} = require(\"@sentry/react-native/metro\");`,\n );\n checkFileContents(\n `${projectDir}/metro.config.js`,\n `module.exports = withSentryConfig(mergeConfig(getDefaultConfig(__dirname), config));`,\n );\n });\n\n test('App.tsx is updated correctly', () => {\n checkFileContents(\n `${projectDir}/App.tsx`,\n `import * as Sentry from '@sentry/react-native';\n\nSentry.init({\n dsn: 'https://public@dsn.ingest.sentry.io/1337',\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 );\n checkFileContents(\n `${projectDir}/App.tsx`,\n `export default Sentry.wrap(App);`,\n );\n });\n\n test('ios/sentry.properties is added', () => {\n if (!podInstallPrompted) {\n return;\n }\n checkFileContents(\n `${projectDir}/ios/sentry.properties`,\n `auth.token=${TEST_ARGS.AUTH_TOKEN}\n\ndefaults.org=${TEST_ARGS.ORG_SLUG}\ndefaults.project=${TEST_ARGS.PROJECT_SLUG}\n\ndefaults.url=https://sentry.io/`,\n );\n });\n\n test('android/sentry.properties is added', () => {\n checkFileContents(\n `${projectDir}/android/sentry.properties`,\n `auth.token=${TEST_ARGS.AUTH_TOKEN}\n\ndefaults.org=${TEST_ARGS.ORG_SLUG}\ndefaults.project=${TEST_ARGS.PROJECT_SLUG}\n\ndefaults.url=https://sentry.io/`,\n );\n });\n\n test('build.gradle is updated correctly', () => {\n checkFileContents(\n `${projectDir}/android/app/build.gradle`,\n `apply from: new File([\"node\", \"--print\", \"require.resolve('@sentry/react-native/package.json')\"].execute().text.trim(), \"../sentry.gradle\")`,\n );\n });\n\n test('xcode project is updated correctly', () => {\n if (!podInstallPrompted) {\n return;\n }\n checkFileContents(\n `${projectDir}/ios/reactnative078.xcodeproj/project.pbxproj`,\n `../node_modules/@sentry/react-native/scripts/sentry-xcode.sh`,\n );\n checkFileContents(\n `${projectDir}/ios/reactnative078.xcodeproj/project.pbxproj`,\n `../node_modules/@sentry/react-native/scripts/sentry-xcode-debug-files.sh`,\n );\n });\n});\n"]}
@@ -114,16 +114,16 @@ function checkRemixProject(projectDir, integration, options) {
114
114
  });
115
115
  (0, vitest_1.test)('entry.client file contains Sentry initialization', () => {
116
116
  (0, utils_1.checkFileContents)(`${projectDir}/app/entry.client.tsx`, [
117
- 'import * as Sentry from "@sentry/remix";',
118
- `Sentry.init({
117
+ 'import { init, replayIntegration, browserTracingIntegration } from "@sentry/remix";',
118
+ `init({
119
119
  dsn: "${utils_1.TEST_ARGS.PROJECT_DSN}",
120
120
  tracesSampleRate: 1,
121
121
 
122
- integrations: [Sentry.browserTracingIntegration({
122
+ integrations: [browserTracingIntegration({
123
123
  useEffect,
124
124
  useLocation,
125
125
  useMatches
126
- }), Sentry.replayIntegration({
126
+ }), replayIntegration({
127
127
  maskAllText: true,
128
128
  blockAllMedia: true
129
129
  })],
@@ -1 +1 @@
1
- {"version":3,"file":"remix.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/remix.test.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AAAA,gDAAkC;AAClC,mDAAkD;AAClD,oCAekB;AAClB,mCAA6D;AAE7D,MAAM,eAAe,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAyCvB,CAAC;AAEF,KAAK,UAAU,uBAAuB,CACpC,UAAkB,EAClB,WAAwB,EACxB,kBAGY;IAEZ,MAAM,cAAc,GAAG,IAAA,2BAAmB,EAAC,WAAW,EAAE,UAAU,CAAC,CAAC;IACpE,IAAI,sBAAsB,GAAG,KAAK,CAAC;IAEnC,IAAI,kBAAkB,EAAE;QACtB,kBAAkB,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC;QAE5C,MAAM,cAAc,CAAC,aAAa,CAAC,iCAAiC,CAAC,CAAC;QAEtE,sBAAsB,GAAG,MAAM,cAAc,CAAC,yBAAyB,CACrE,CAAC,YAAI,CAAC,KAAK,CAAC,EACZ,qCAAqC,CACtC,CAAC;KACH;SAAM;QACL,sBAAsB,GAAG,MAAM,cAAc,CAAC,aAAa,CACzD,qCAAqC,CACtC,CAAC;KACH;IAED,MAAM,qBAAqB,GACzB,sBAAsB;QACtB,CAAC,MAAM,cAAc,CAAC,yBAAyB;QAC7C,0CAA0C;QAC1C,CAAC,YAAI,CAAC,IAAI,EAAE,YAAI,CAAC,KAAK,CAAC;QACvB,+FAA+F;QAC/F,+CAA+C,EAC/C;YACE,OAAO,EAAE,MAAO;SACjB,CACF,CAAC,CAAC;IAEL,MAAM,oBAAoB,GACxB,qBAAqB;QACrB,CAAC,MAAM,cAAc,CAAC,yBAAyB,CAC7C,CAAC,YAAI,CAAC,KAAK,CAAC;QACZ,2HAA2H;QAC3H,mEAAmE,CACpE,CAAC,CAAC;IAEL,oBAAoB;QAClB,CAAC,MAAM,cAAc,CAAC,yBAAyB,CAC7C,CAAC,YAAI,CAAC,KAAK,CAAC,EACZ,uCAAuC,EACvC;YACE,QAAQ,EAAE,IAAI;SACf,CACF,CAAC,CAAC;IAEL,MAAM,cAAc,CAAC,yBAAyB,CAC5C,CAAC,YAAI,CAAC,KAAK,EAAE,YAAI,CAAC,KAAK,CAAC,EACxB,gEAAgE,CACjE,CAAC;IAEF,cAAc,CAAC,IAAI,EAAE,CAAC;AACxB,CAAC;AAED,SAAS,iBAAiB,CACxB,UAAkB,EAClB,WAAwB,EACxB,OAGC;IAED,IAAA,aAAI,EAAC,mCAAmC,EAAE,GAAG,EAAE;QAC7C,IAAA,wBAAgB,EAAC,UAAU,EAAE,WAAW,CAAC,CAAC;IAC5C,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,iEAAiE,EAAE,GAAG,EAAE;QAC3E,IAAA,2BAAmB,EAAC,UAAU,CAAC,CAAC;IAClC,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,qBAAqB,EAAE,GAAG,EAAE;QAC/B,IAAA,uBAAe,EAAC,GAAG,UAAU,qCAAqC,CAAC,CAAC;IACtE,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,oCAAoC,EAAE,GAAG,EAAE;QAC9C,IAAA,uBAAe,EAAC,GAAG,UAAU,6BAA6B,CAAC,CAAC;IAC9D,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,kDAAkD,EAAE,GAAG,EAAE;QAC5D,IAAA,yBAAiB,EAAC,GAAG,UAAU,uBAAuB,EAAE;YACtD,0CAA0C;YAC1C;YACM,iBAAS,CAAC,WAAW;;;;;;;;;;;;;;GAc9B;SACE,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,wCAAwC,EAAE,GAAG,EAAE;QAClD,IAAA,yBAAiB,EAAC,GAAG,UAAU,uBAAuB,EAAE;YACtD,0CAA0C;YAC1C;;IAEF;SACC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,4DAA4D,EAAE,GAAG,EAAE;QACtE,IAAA,yBAAiB,EAAC,GAAG,UAAU,6BAA6B,EAAE;YAC5D,0CAA0C;YAC1C;YACM,iBAAS,CAAC,WAAW;;GAE9B;SACE,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,yCAAyC,EAAE,GAAG,EAAE;QACnD,IAAA,yBAAiB,EAAC,GAAG,UAAU,eAAe,EAAE;YAC9C,iEAAiE;YACjE;;;;GAIH;SACE,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,qBAAqB,EAAE,KAAK,IAAI,EAAE;QACrC,MAAM,IAAA,qBAAa,EAAC,UAAU,CAAC,CAAC;IAClC,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,4BAA4B,EAAE,KAAK,IAAI,EAAE;QAC5C,MAAM,IAAA,4BAAoB,EACxB,UAAU,EACV,OAAO,EAAE,qBAAqB,IAAI,WAAW,CAC9C,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,IAAA,aAAI,EAAC,6BAA6B,EAAE,KAAK,IAAI,EAAE;QAC7C,MAAM,IAAA,6BAAqB,EACzB,UAAU,EACV,OAAO,EAAE,sBAAsB,IAAI,eAAe,CACnD,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC;AAED,IAAA,iBAAQ,EAAC,OAAO,EAAE,GAAG,EAAE;IACrB,IAAA,iBAAQ,EAAC,oBAAoB,EAAE,GAAG,EAAE;QAClC,MAAM,WAAW,GAAG,uBAAW,CAAC,KAAK,CAAC;QACtC,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,CAC7B,SAAS,EACT,qCAAqC,CACtC,CAAC;QAEF,IAAA,kBAAS,EAAC,KAAK,IAAI,EAAE;YACnB,MAAM,uBAAuB,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC;QACzD,CAAC,CAAC,CAAC;QAEH,IAAA,iBAAQ,EAAC,GAAG,EAAE;YACZ,IAAA,0BAAkB,EAAC,UAAU,CAAC,CAAC;YAC/B,IAAA,kBAAU,EAAC,UAAU,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QAEH,iBAAiB,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC;IAC7C,CAAC,CAAC,CAAC;IAEH,IAAA,iBAAQ,EAAC,qCAAqC,EAAE,GAAG,EAAE;QACnD,MAAM,WAAW,GAAG,uBAAW,CAAC,KAAK,CAAC;QACtC,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,CAC7B,SAAS,EACT,qCAAqC,CACtC,CAAC;QAEF,IAAA,kBAAS,EAAC,KAAK,IAAI,EAAE;YACnB,MAAM,uBAAuB,CAAC,UAAU,EAAE,WAAW,EAAE,CAAC,UAAU,EAAE,EAAE;gBACpE,IAAA,kBAAU,EAAC,GAAG,UAAU,aAAa,EAAE,eAAe,CAAC,CAAC;gBAExD,IAAA,kBAAU,EAAC,GAAG,UAAU,eAAe,EAAE;oBACvC,gDAAgD,EAC9C,8BAA8B;oBAChC,yBAAyB,EAAE,4BAA4B;iBACxD,CAAC,CAAC;YACL,CAAC,CAAC,CAAC;QACL,CAAC,CAAC,CAAC;QAEH,IAAA,iBAAQ,EAAC,GAAG,EAAE;YACZ,IAAA,0BAAkB,EAAC,UAAU,CAAC,CAAC;YAC/B,IAAA,kBAAU,EAAC,UAAU,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QAEH,iBAAiB,CAAC,UAAU,EAAE,WAAW,EAAE;YACzC,qBAAqB,EAAE,0BAA0B;YACjD,sBAAsB,EAAE,0BAA0B;SACnD,CAAC,CAAC;QAEH,IAAA,aAAI,EAAC,iDAAiD,EAAE,GAAG,EAAE;YAC3D,IAAA,yBAAiB,EAAC,GAAG,UAAU,aAAa,EAAE;gBAC5C,wCAAwC;aACzC,CAAC,CAAC;QACL,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport {\n KEYS,\n TEST_ARGS,\n checkEnvBuildPlugin,\n checkFileContents,\n checkFileExists,\n checkIfBuilds,\n checkIfRunsOnDevMode,\n checkIfRunsOnProdMode,\n checkPackageJson,\n cleanupGit,\n createFile,\n modifyFile,\n revertLocalChanges,\n startWizardInstance,\n} from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\nconst SERVER_TEMPLATE = `import { createRequestHandler } from '@remix-run/express';\nimport { installGlobals } from '@remix-run/node';\nimport compression from 'compression';\nimport express from 'express';\nimport morgan from 'morgan';\n\ninstallGlobals();\n\nconst viteDevServer =\n process.env.NODE_ENV === 'production'\n ? undefined\n : await import('vite').then(vite =>\n vite.createServer({\n server: { middlewareMode: true },\n }),\n );\n\nconst app = express();\n\napp.use(compression());\napp.disable('x-powered-by');\n\nif (viteDevServer) {\n app.use(viteDevServer.middlewares);\n} else {\n app.use('/assets', express.static('build/client/assets', { immutable: true, maxAge: '1y' }));\n}\n\napp.use(express.static('build/client', { maxAge: '1h' }));\napp.use(morgan('tiny'));\n\napp.all(\n '*',\n createRequestHandler({\n build: viteDevServer\n ? () => viteDevServer.ssrLoadModule('virtual:remix/server-build')\n : await import('./build/server/index.js'),\n }),\n);\n\napp.listen(0, () => console.log('Express server listening'));\n`;\n\nasync function runWizardOnRemixProject(\n projectDir: string,\n integration: Integration,\n fileModificationFn?: (\n projectDir: string,\n integration: Integration,\n ) => unknown,\n) {\n const wizardInstance = startWizardInstance(integration, projectDir);\n let packageManagerPrompted = false;\n\n if (fileModificationFn) {\n fileModificationFn(projectDir, integration);\n\n await wizardInstance.waitForOutput('Do you want to continue anyway?');\n\n packageManagerPrompted = await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Please select your package manager.',\n );\n } else {\n packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager.',\n );\n }\n\n const tracingOptionPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.ENTER],\n // \"Do you want to enable Tracing\", sometimes doesn't work as `Tracing` can be printed in bold.\n 'to track the performance of your application?',\n {\n timeout: 240_000,\n },\n ));\n\n const replayOptionPrompted =\n tracingOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n // \"Do you want to enable Sentry Session Replay\", sometimes doesn't work as `Sentry Session Replay` can be printed in bold.\n 'to get a video-like reproduction of errors during a user session?',\n ));\n\n replayOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Do you want to create an example page',\n {\n optional: true,\n },\n ));\n\n await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER, KEYS.ENTER],\n 'Sentry has been successfully configured for your Remix project',\n );\n\n wizardInstance.kill();\n}\n\nfunction checkRemixProject(\n projectDir: string,\n integration: Integration,\n options?: {\n devModeExpectedOutput?: string;\n prodModeExpectedOutput?: string;\n },\n) {\n test('package.json is updated correctly', () => {\n checkPackageJson(projectDir, integration);\n });\n\n test('.env-sentry-build-plugin is created and contains the auth token', () => {\n checkEnvBuildPlugin(projectDir);\n });\n\n test('example page exists', () => {\n checkFileExists(`${projectDir}/app/routes/sentry-example-page.tsx`);\n });\n\n test('instrumentation.server file exists', () => {\n checkFileExists(`${projectDir}/instrumentation.server.mjs`);\n });\n\n test('entry.client file contains Sentry initialization', () => {\n checkFileContents(`${projectDir}/app/entry.client.tsx`, [\n 'import * as Sentry from \"@sentry/remix\";',\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1,\n\n integrations: [Sentry.browserTracingIntegration({\n useEffect,\n useLocation,\n useMatches\n }), Sentry.replayIntegration({\n maskAllText: true,\n blockAllMedia: true\n })],\n\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1\n})`,\n ]);\n });\n\n test('entry.server file contains Sentry code', () => {\n checkFileContents(`${projectDir}/app/entry.server.tsx`, [\n 'import * as Sentry from \"@sentry/remix\";',\n `export const handleError = Sentry.wrapHandleErrorWithSentry((error, { request }) => {\n // Custom handleError implementation\n});`,\n ]);\n });\n\n test('instrumentation.server file contains Sentry initialization', () => {\n checkFileContents(`${projectDir}/instrumentation.server.mjs`, [\n 'import * as Sentry from \"@sentry/remix\";',\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1\n})`,\n ]);\n });\n\n test('root file contains Sentry ErrorBoundary', () => {\n checkFileContents(`${projectDir}/app/root.tsx`, [\n 'import { captureRemixErrorBoundaryError } from \"@sentry/remix\";',\n `export const ErrorBoundary = () => {\n const error = useRouteError();\n captureRemixErrorBoundaryError(error);\n return <div>Something went wrong</div>;\n};`,\n ]);\n });\n\n test('builds successfully', async () => {\n await checkIfBuilds(projectDir);\n });\n\n test('runs on dev mode correctly', async () => {\n await checkIfRunsOnDevMode(\n projectDir,\n options?.devModeExpectedOutput || 'to expose',\n );\n });\n\n test('runs on prod mode correctly', async () => {\n await checkIfRunsOnProdMode(\n projectDir,\n options?.prodModeExpectedOutput || '[remix-serve]',\n );\n });\n}\n\ndescribe('Remix', () => {\n describe('with empty project', () => {\n const integration = Integration.remix;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/remix-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnRemixProject(projectDir, integration);\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkRemixProject(projectDir, integration);\n });\n\n describe('with existing custom Express server', () => {\n const integration = Integration.remix;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/remix-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnRemixProject(projectDir, integration, (projectDir) => {\n createFile(`${projectDir}/server.mjs`, SERVER_TEMPLATE);\n\n modifyFile(`${projectDir}/package.json`, {\n '\"start\": \"remix-serve ./build/server/index.js\"':\n '\"start\": \"node ./server.mjs\"',\n '\"dev\": \"remix vite:dev\"': '\"dev\": \"node ./server.mjs\"',\n });\n });\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkRemixProject(projectDir, integration, {\n devModeExpectedOutput: 'Express server listening',\n prodModeExpectedOutput: 'Express server listening',\n });\n\n test('server.mjs contains instrumentation file import', () => {\n checkFileContents(`${projectDir}/server.mjs`, [\n \"import './instrumentation.server.mjs';\",\n ]);\n });\n });\n});\n"]}
1
+ {"version":3,"file":"remix.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/remix.test.ts"],"names":[],"mappings":"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","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport {\n KEYS,\n TEST_ARGS,\n checkEnvBuildPlugin,\n checkFileContents,\n checkFileExists,\n checkIfBuilds,\n checkIfRunsOnDevMode,\n checkIfRunsOnProdMode,\n checkPackageJson,\n cleanupGit,\n createFile,\n modifyFile,\n revertLocalChanges,\n startWizardInstance,\n} from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\nconst SERVER_TEMPLATE = `import { createRequestHandler } from '@remix-run/express';\nimport { installGlobals } from '@remix-run/node';\nimport compression from 'compression';\nimport express from 'express';\nimport morgan from 'morgan';\n\ninstallGlobals();\n\nconst viteDevServer =\n process.env.NODE_ENV === 'production'\n ? undefined\n : await import('vite').then(vite =>\n vite.createServer({\n server: { middlewareMode: true },\n }),\n );\n\nconst app = express();\n\napp.use(compression());\napp.disable('x-powered-by');\n\nif (viteDevServer) {\n app.use(viteDevServer.middlewares);\n} else {\n app.use('/assets', express.static('build/client/assets', { immutable: true, maxAge: '1y' }));\n}\n\napp.use(express.static('build/client', { maxAge: '1h' }));\napp.use(morgan('tiny'));\n\napp.all(\n '*',\n createRequestHandler({\n build: viteDevServer\n ? () => viteDevServer.ssrLoadModule('virtual:remix/server-build')\n : await import('./build/server/index.js'),\n }),\n);\n\napp.listen(0, () => console.log('Express server listening'));\n`;\n\nasync function runWizardOnRemixProject(\n projectDir: string,\n integration: Integration,\n fileModificationFn?: (\n projectDir: string,\n integration: Integration,\n ) => unknown,\n) {\n const wizardInstance = startWizardInstance(integration, projectDir);\n let packageManagerPrompted = false;\n\n if (fileModificationFn) {\n fileModificationFn(projectDir, integration);\n\n await wizardInstance.waitForOutput('Do you want to continue anyway?');\n\n packageManagerPrompted = await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Please select your package manager.',\n );\n } else {\n packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager.',\n );\n }\n\n const tracingOptionPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.ENTER],\n // \"Do you want to enable Tracing\", sometimes doesn't work as `Tracing` can be printed in bold.\n 'to track the performance of your application?',\n {\n timeout: 240_000,\n },\n ));\n\n const replayOptionPrompted =\n tracingOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n // \"Do you want to enable Sentry Session Replay\", sometimes doesn't work as `Sentry Session Replay` can be printed in bold.\n 'to get a video-like reproduction of errors during a user session?',\n ));\n\n replayOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Do you want to create an example page',\n {\n optional: true,\n },\n ));\n\n await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER, KEYS.ENTER],\n 'Sentry has been successfully configured for your Remix project',\n );\n\n wizardInstance.kill();\n}\n\nfunction checkRemixProject(\n projectDir: string,\n integration: Integration,\n options?: {\n devModeExpectedOutput?: string;\n prodModeExpectedOutput?: string;\n },\n) {\n test('package.json is updated correctly', () => {\n checkPackageJson(projectDir, integration);\n });\n\n test('.env-sentry-build-plugin is created and contains the auth token', () => {\n checkEnvBuildPlugin(projectDir);\n });\n\n test('example page exists', () => {\n checkFileExists(`${projectDir}/app/routes/sentry-example-page.tsx`);\n });\n\n test('instrumentation.server file exists', () => {\n checkFileExists(`${projectDir}/instrumentation.server.mjs`);\n });\n\n test('entry.client file contains Sentry initialization', () => {\n checkFileContents(`${projectDir}/app/entry.client.tsx`, [\n 'import { init, replayIntegration, browserTracingIntegration } from \"@sentry/remix\";',\n `init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1,\n\n integrations: [browserTracingIntegration({\n useEffect,\n useLocation,\n useMatches\n }), replayIntegration({\n maskAllText: true,\n blockAllMedia: true\n })],\n\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1\n})`,\n ]);\n });\n\n test('entry.server file contains Sentry code', () => {\n checkFileContents(`${projectDir}/app/entry.server.tsx`, [\n 'import * as Sentry from \"@sentry/remix\";',\n `export const handleError = Sentry.wrapHandleErrorWithSentry((error, { request }) => {\n // Custom handleError implementation\n});`,\n ]);\n });\n\n test('instrumentation.server file contains Sentry initialization', () => {\n checkFileContents(`${projectDir}/instrumentation.server.mjs`, [\n 'import * as Sentry from \"@sentry/remix\";',\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1\n})`,\n ]);\n });\n\n test('root file contains Sentry ErrorBoundary', () => {\n checkFileContents(`${projectDir}/app/root.tsx`, [\n 'import { captureRemixErrorBoundaryError } from \"@sentry/remix\";',\n `export const ErrorBoundary = () => {\n const error = useRouteError();\n captureRemixErrorBoundaryError(error);\n return <div>Something went wrong</div>;\n};`,\n ]);\n });\n\n test('builds successfully', async () => {\n await checkIfBuilds(projectDir);\n });\n\n test('runs on dev mode correctly', async () => {\n await checkIfRunsOnDevMode(\n projectDir,\n options?.devModeExpectedOutput || 'to expose',\n );\n });\n\n test('runs on prod mode correctly', async () => {\n await checkIfRunsOnProdMode(\n projectDir,\n options?.prodModeExpectedOutput || '[remix-serve]',\n );\n });\n}\n\ndescribe('Remix', () => {\n describe('with empty project', () => {\n const integration = Integration.remix;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/remix-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnRemixProject(projectDir, integration);\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkRemixProject(projectDir, integration);\n });\n\n describe('with existing custom Express server', () => {\n const integration = Integration.remix;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/remix-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnRemixProject(projectDir, integration, (projectDir) => {\n createFile(`${projectDir}/server.mjs`, SERVER_TEMPLATE);\n\n modifyFile(`${projectDir}/package.json`, {\n '\"start\": \"remix-serve ./build/server/index.js\"':\n '\"start\": \"node ./server.mjs\"',\n '\"dev\": \"remix vite:dev\"': '\"dev\": \"node ./server.mjs\"',\n });\n });\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkRemixProject(projectDir, integration, {\n devModeExpectedOutput: 'Express server listening',\n prodModeExpectedOutput: 'Express server listening',\n });\n\n test('server.mjs contains instrumentation file import', () => {\n checkFileContents(`${projectDir}/server.mjs`, [\n \"import './instrumentation.server.mjs';\",\n ]);\n });\n });\n});\n"]}
@@ -89,8 +89,8 @@ function checkSvelteKitProject(projectDir, integration, options) {
89
89
  (0, utils_1.checkEnvBuildPlugin)(projectDir);
90
90
  });
91
91
  (0, vitest_1.test)('example page exists', () => {
92
- (0, utils_1.checkFileExists)(path.resolve(projectDir, 'src/routes/sentry-example/+page.svelte'));
93
- (0, utils_1.checkFileExists)(path.resolve(projectDir, 'src/routes/sentry-example/+server.js'));
92
+ (0, utils_1.checkFileExists)(path.resolve(projectDir, 'src/routes/sentry-example-page/+page.svelte'));
93
+ (0, utils_1.checkFileExists)(path.resolve(projectDir, 'src/routes/sentry-example-page/+server.js'));
94
94
  });
95
95
  (0, vitest_1.test)('vite.config contains sentry plugin', () => {
96
96
  (0, utils_1.checkFileContents)(path.resolve(projectDir, 'vite.config.ts'), `plugins: [sentrySvelteKit({
@@ -1 +1 @@
1
- {"version":3,"file":"sveltekit.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/sveltekit.test.ts"],"names":[],"mappings":"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","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport {\n KEYS,\n TEST_ARGS,\n checkEnvBuildPlugin,\n checkFileContents,\n checkFileExists,\n checkIfBuilds,\n checkIfRunsOnDevMode,\n checkIfRunsOnProdMode,\n checkPackageJson,\n cleanupGit,\n createFile,\n revertLocalChanges,\n startWizardInstance,\n} from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\nconst SERVER_HOOK_TEMPLATE = `import type { Handle } from '@sveltejs/kit';\n\nexport const handle: Handle = async ({ event, resolve }) => {\n\tif (event.url.pathname.startsWith('/custom')) {\n\t\treturn new Response('custom response');\n\t}\n\n\tconst response = await resolve(event);\n\treturn response;\n};\n`;\nconst CLIENT_HOOK_TEMPLATE = `\nexport async function handleError({ error, event }) {\n // you can capture the \\`error\\` and \\`event\\` from the client\n // but it only runs if the unexpected error comes from \\`+ page.ts\\`\n console.log(error)\n\n return {\n // don't show sensitive data to the user\n message: 'Yikes! 💩',\n }\n}\n`;\n\nasync function runWizardOnSvelteKitProject(\n projectDir: string,\n integration: Integration,\n fileModificationFn?: (\n projectDir: string,\n integration: Integration,\n ) => unknown,\n) {\n const wizardInstance = startWizardInstance(integration, projectDir);\n let packageManagerPrompted = false;\n\n if (fileModificationFn) {\n fileModificationFn(projectDir, integration);\n\n // As we modified project, we have a warning prompt before we get the package manager prompt\n await wizardInstance.waitForOutput('Do you want to continue anyway?');\n\n packageManagerPrompted = await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Please select your package manager.',\n );\n } else {\n packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager',\n );\n }\n\n const tracingOptionPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.ENTER],\n // \"Do you want to enable Tracing\", sometimes doesn't work as `Tracing` can be printed in bold.\n 'to track the performance of your application?',\n {\n timeout: 240_000,\n },\n ));\n\n const replayOptionPrompted =\n tracingOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n // \"Do you want to enable Sentry Session Replay\", sometimes doesn't work as `Sentry Session Replay` can be printed in bold.\n 'to get a video-like reproduction of errors during a user session?',\n ));\n\n replayOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Do you want to create an example page',\n {\n optional: true,\n },\n ));\n\n await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER, KEYS.ENTER],\n 'Successfully installed the Sentry SvelteKit SDK!',\n );\n\n wizardInstance.kill();\n}\n\nfunction checkSvelteKitProject(\n projectDir: string,\n integration: Integration,\n options?: {\n devModeExpectedOutput: string;\n prodModeExpectedOutput: string;\n },\n) {\n test('should have the correct package.json', () => {\n checkPackageJson(projectDir, integration);\n });\n\n test('should have the correct .env.sentry-build-plugin', () => {\n checkEnvBuildPlugin(projectDir);\n });\n\n test('example page exists', () => {\n checkFileExists(\n path.resolve(projectDir, 'src/routes/sentry-example/+page.svelte'),\n );\n checkFileExists(\n path.resolve(projectDir, 'src/routes/sentry-example/+server.js'),\n );\n });\n\n test('vite.config contains sentry plugin', () => {\n checkFileContents(\n path.resolve(projectDir, 'vite.config.ts'),\n `plugins: [sentrySvelteKit({\n sourceMapsUploadOptions: {\n`,\n );\n });\n\n test('hook files created', () => {\n checkFileExists(path.resolve(projectDir, 'src/hooks.server.ts'));\n checkFileExists(path.resolve(projectDir, 'src/hooks.client.ts'));\n });\n\n test('builds successfully', async () => {\n await checkIfBuilds(projectDir);\n });\n\n test('runs on dev mode correctly', async () => {\n await checkIfRunsOnDevMode(\n projectDir,\n options?.devModeExpectedOutput || 'ready in',\n );\n });\n\n test('runs on prod mode correctly', async () => {\n await checkIfRunsOnProdMode(\n projectDir,\n options?.prodModeExpectedOutput || 'to expose',\n 'preview',\n );\n });\n}\n\ndescribe('Sveltekit', () => {\n describe('without existing hooks', () => {\n const integration = Integration.sveltekit;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/sveltekit-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnSvelteKitProject(projectDir, integration);\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkSvelteKitProject(projectDir, integration);\n\n test('hooks.client.ts contains sentry', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.client.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: '${TEST_ARGS.PROJECT_DSN}',\n\n tracesSampleRate: 1.0,\n\n // This sets the sample rate to be 10%. You may want this to be 100% while\n // in development and sample at a lower rate in production\n replaysSessionSampleRate: 0.1,\n\n // If the entire session is not sampled, use the below sample rate to sample\n // sessions when an error occurs.\n replaysOnErrorSampleRate: 1.0,\n\n // If you don't want to use Session Replay, just remove the line below:\n integrations: [replayIntegration()],\n});`,\n 'export const handleError = handleErrorWithSentry(',\n ]);\n });\n\n test('hooks.server.ts contains sentry', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.server.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: '${TEST_ARGS.PROJECT_DSN}',\n\n tracesSampleRate: 1.0,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: import.meta.env.DEV,\n});`,\n 'export const handleError = handleErrorWithSentry();',\n ]);\n });\n });\n\n describe('with existing hooks', () => {\n const integration = Integration.sveltekit;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/sveltekit-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnSvelteKitProject(\n projectDir,\n integration,\n (projectDir) => {\n createFile(\n path.resolve(projectDir, 'src/hooks.server.ts'),\n SERVER_HOOK_TEMPLATE,\n );\n\n createFile(\n path.resolve(projectDir, 'src/hooks.client.ts'),\n CLIENT_HOOK_TEMPLATE,\n );\n },\n );\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkSvelteKitProject(projectDir, integration);\n\n // These are removed from the common tests as the content is different\n // when the hooks are merged instead of created from the template\n test('hooks.client.ts contains sentry instrumentation', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.client.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1,\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.replayIntegration()]\n})`,\n 'export const handleError = Sentry.handleErrorWithSentry(',\n ]);\n });\n\n test('hooks.server.ts contains sentry init', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.server.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1\n})`,\n 'export const handleError = Sentry.handleErrorWithSentry();',\n ]);\n });\n });\n});\n"]}
1
+ {"version":3,"file":"sveltekit.test.js","sourceRoot":"","sources":["../../../e2e-tests/tests/sveltekit.test.ts"],"names":[],"mappings":"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","sourcesContent":["import * as path from 'node:path';\nimport { Integration } from '../../lib/Constants';\nimport {\n KEYS,\n TEST_ARGS,\n checkEnvBuildPlugin,\n checkFileContents,\n checkFileExists,\n checkIfBuilds,\n checkIfRunsOnDevMode,\n checkIfRunsOnProdMode,\n checkPackageJson,\n cleanupGit,\n createFile,\n revertLocalChanges,\n startWizardInstance,\n} from '../utils';\nimport { afterAll, beforeAll, describe, test } from 'vitest';\n\nconst SERVER_HOOK_TEMPLATE = `import type { Handle } from '@sveltejs/kit';\n\nexport const handle: Handle = async ({ event, resolve }) => {\n\tif (event.url.pathname.startsWith('/custom')) {\n\t\treturn new Response('custom response');\n\t}\n\n\tconst response = await resolve(event);\n\treturn response;\n};\n`;\nconst CLIENT_HOOK_TEMPLATE = `\nexport async function handleError({ error, event }) {\n // you can capture the \\`error\\` and \\`event\\` from the client\n // but it only runs if the unexpected error comes from \\`+ page.ts\\`\n console.log(error)\n\n return {\n // don't show sensitive data to the user\n message: 'Yikes! 💩',\n }\n}\n`;\n\nasync function runWizardOnSvelteKitProject(\n projectDir: string,\n integration: Integration,\n fileModificationFn?: (\n projectDir: string,\n integration: Integration,\n ) => unknown,\n) {\n const wizardInstance = startWizardInstance(integration, projectDir);\n let packageManagerPrompted = false;\n\n if (fileModificationFn) {\n fileModificationFn(projectDir, integration);\n\n // As we modified project, we have a warning prompt before we get the package manager prompt\n await wizardInstance.waitForOutput('Do you want to continue anyway?');\n\n packageManagerPrompted = await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Please select your package manager.',\n );\n } else {\n packageManagerPrompted = await wizardInstance.waitForOutput(\n 'Please select your package manager',\n );\n }\n\n const tracingOptionPrompted =\n packageManagerPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n // Selecting `yarn` as the package manager\n [KEYS.DOWN, KEYS.ENTER],\n // \"Do you want to enable Tracing\", sometimes doesn't work as `Tracing` can be printed in bold.\n 'to track the performance of your application?',\n {\n timeout: 240_000,\n },\n ));\n\n const replayOptionPrompted =\n tracingOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n // \"Do you want to enable Sentry Session Replay\", sometimes doesn't work as `Sentry Session Replay` can be printed in bold.\n 'to get a video-like reproduction of errors during a user session?',\n ));\n\n replayOptionPrompted &&\n (await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER],\n 'Do you want to create an example page',\n {\n optional: true,\n },\n ));\n\n await wizardInstance.sendStdinAndWaitForOutput(\n [KEYS.ENTER, KEYS.ENTER],\n 'Successfully installed the Sentry SvelteKit SDK!',\n );\n\n wizardInstance.kill();\n}\n\nfunction checkSvelteKitProject(\n projectDir: string,\n integration: Integration,\n options?: {\n devModeExpectedOutput: string;\n prodModeExpectedOutput: string;\n },\n) {\n test('should have the correct package.json', () => {\n checkPackageJson(projectDir, integration);\n });\n\n test('should have the correct .env.sentry-build-plugin', () => {\n checkEnvBuildPlugin(projectDir);\n });\n\n test('example page exists', () => {\n checkFileExists(\n path.resolve(projectDir, 'src/routes/sentry-example-page/+page.svelte'),\n );\n checkFileExists(\n path.resolve(projectDir, 'src/routes/sentry-example-page/+server.js'),\n );\n });\n\n test('vite.config contains sentry plugin', () => {\n checkFileContents(\n path.resolve(projectDir, 'vite.config.ts'),\n `plugins: [sentrySvelteKit({\n sourceMapsUploadOptions: {\n`,\n );\n });\n\n test('hook files created', () => {\n checkFileExists(path.resolve(projectDir, 'src/hooks.server.ts'));\n checkFileExists(path.resolve(projectDir, 'src/hooks.client.ts'));\n });\n\n test('builds successfully', async () => {\n await checkIfBuilds(projectDir);\n });\n\n test('runs on dev mode correctly', async () => {\n await checkIfRunsOnDevMode(\n projectDir,\n options?.devModeExpectedOutput || 'ready in',\n );\n });\n\n test('runs on prod mode correctly', async () => {\n await checkIfRunsOnProdMode(\n projectDir,\n options?.prodModeExpectedOutput || 'to expose',\n 'preview',\n );\n });\n}\n\ndescribe('Sveltekit', () => {\n describe('without existing hooks', () => {\n const integration = Integration.sveltekit;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/sveltekit-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnSvelteKitProject(projectDir, integration);\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkSvelteKitProject(projectDir, integration);\n\n test('hooks.client.ts contains sentry', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.client.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: '${TEST_ARGS.PROJECT_DSN}',\n\n tracesSampleRate: 1.0,\n\n // This sets the sample rate to be 10%. You may want this to be 100% while\n // in development and sample at a lower rate in production\n replaysSessionSampleRate: 0.1,\n\n // If the entire session is not sampled, use the below sample rate to sample\n // sessions when an error occurs.\n replaysOnErrorSampleRate: 1.0,\n\n // If you don't want to use Session Replay, just remove the line below:\n integrations: [replayIntegration()],\n});`,\n 'export const handleError = handleErrorWithSentry(',\n ]);\n });\n\n test('hooks.server.ts contains sentry', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.server.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: '${TEST_ARGS.PROJECT_DSN}',\n\n tracesSampleRate: 1.0,\n\n // uncomment the line below to enable Spotlight (https://spotlightjs.com)\n // spotlight: import.meta.env.DEV,\n});`,\n 'export const handleError = handleErrorWithSentry();',\n ]);\n });\n });\n\n describe('with existing hooks', () => {\n const integration = Integration.sveltekit;\n const projectDir = path.resolve(\n __dirname,\n '../test-applications/sveltekit-test-app',\n );\n\n beforeAll(async () => {\n await runWizardOnSvelteKitProject(\n projectDir,\n integration,\n (projectDir) => {\n createFile(\n path.resolve(projectDir, 'src/hooks.server.ts'),\n SERVER_HOOK_TEMPLATE,\n );\n\n createFile(\n path.resolve(projectDir, 'src/hooks.client.ts'),\n CLIENT_HOOK_TEMPLATE,\n );\n },\n );\n });\n\n afterAll(() => {\n revertLocalChanges(projectDir);\n cleanupGit(projectDir);\n });\n\n checkSvelteKitProject(projectDir, integration);\n\n // These are removed from the common tests as the content is different\n // when the hooks are merged instead of created from the template\n test('hooks.client.ts contains sentry instrumentation', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.client.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1,\n replaysSessionSampleRate: 0.1,\n replaysOnErrorSampleRate: 1,\n integrations: [Sentry.replayIntegration()]\n})`,\n 'export const handleError = Sentry.handleErrorWithSentry(',\n ]);\n });\n\n test('hooks.server.ts contains sentry init', () => {\n checkFileContents(path.resolve(projectDir, 'src/hooks.server.ts'), [\n `import * as Sentry from '@sentry/sveltekit';`,\n `Sentry.init({\n dsn: \"${TEST_ARGS.PROJECT_DSN}\",\n tracesSampleRate: 1\n})`,\n 'export const handleError = Sentry.handleErrorWithSentry();',\n ]);\n });\n });\n});\n"]}
@@ -105,6 +105,13 @@ export declare function createFile(filePath: string, content?: string): void;
105
105
  * @param newContent
106
106
  */
107
107
  export declare function modifyFile(filePath: string, replaceMap: Record<string, string>): void;
108
+ /**
109
+ * Read the file contents and check if it does not contain the given content
110
+ *
111
+ * @param {string} filePath
112
+ * @param {(string | string[])} content
113
+ */
114
+ export declare function checkFileDoesNotContain(filePath: string, content: string | string[]): void;
108
115
  /**
109
116
  * Read the file contents and check if it contains the given content
110
117
  *
@@ -23,7 +23,7 @@ var __importStar = (this && this.__importStar) || function (mod) {
23
23
  return result;
24
24
  };
25
25
  Object.defineProperty(exports, "__esModule", { value: true });
26
- exports.checkIfRunsOnProdMode = exports.checkIfRunsOnDevMode = exports.checkIfFlutterBuilds = exports.checkIfBuilds = exports.checkSentryProperties = exports.checkEnvBuildPlugin = exports.checkSentryCliRc = exports.checkPackageJson = exports.checkFileExists = exports.checkFileContents = exports.modifyFile = exports.createFile = exports.startWizardInstance = exports.revertLocalChanges = exports.cleanupGit = exports.initGit = exports.WizardTestEnv = exports.log = exports.TEST_ARGS = exports.KEYS = void 0;
26
+ exports.checkIfRunsOnProdMode = exports.checkIfRunsOnDevMode = exports.checkIfFlutterBuilds = exports.checkIfBuilds = exports.checkSentryProperties = exports.checkEnvBuildPlugin = exports.checkSentryCliRc = exports.checkPackageJson = exports.checkFileExists = exports.checkFileContents = exports.checkFileDoesNotContain = exports.modifyFile = exports.createFile = exports.startWizardInstance = exports.revertLocalChanges = exports.cleanupGit = exports.initGit = exports.WizardTestEnv = exports.log = exports.TEST_ARGS = exports.KEYS = void 0;
27
27
  const fs = __importStar(require("node:fs"));
28
28
  const path = __importStar(require("node:path"));
29
29
  const node_child_process_1 = require("node:child_process");
@@ -142,6 +142,8 @@ class WizardTestEnv {
142
142
  return new Promise((resolve, reject) => {
143
143
  let outputBuffer = '';
144
144
  const timeoutId = setTimeout(() => {
145
+ this.taskHandle.off('error', errorListener);
146
+ this.taskHandle.stdout?.off('data', dataListener);
145
147
  this.kill();
146
148
  if (optional) {
147
149
  // The output is not found but it's optional so we can resolve the promise with false
@@ -151,18 +153,24 @@ class WizardTestEnv {
151
153
  reject(new Error(`Timeout waiting for output: ${output}. Got the following instead: ${outputBuffer}`));
152
154
  }
153
155
  }, timeout);
154
- this.taskHandle.on('error', (err) => {
155
- clearTimeout(timeoutId);
156
- reject(err);
157
- });
158
- this.taskHandle.stdout?.on('data', (data) => {
156
+ const dataListener = (data) => {
159
157
  outputBuffer += data;
160
158
  if (outputBuffer.includes(output)) {
161
159
  clearTimeout(timeoutId);
160
+ this.taskHandle.off('error', errorListener);
161
+ this.taskHandle.stdout?.off('data', dataListener);
162
162
  // The output is found so we can resolve the promise with true
163
163
  resolve(true);
164
164
  }
165
- });
165
+ };
166
+ const errorListener = (err) => {
167
+ this.taskHandle.off('error', errorListener);
168
+ this.taskHandle.stdout?.off('data', dataListener);
169
+ clearTimeout(timeoutId);
170
+ reject(err);
171
+ };
172
+ this.taskHandle.on('error', errorListener);
173
+ this.taskHandle.stdout?.on('data', dataListener);
166
174
  });
167
175
  }
168
176
  kill() {
@@ -226,6 +234,9 @@ function revertLocalChanges(projectDir) {
226
234
  (0, node_child_process_1.execSync)('git restore .', { cwd: projectDir });
227
235
  // Revert untracked files
228
236
  (0, node_child_process_1.execSync)('git clean -fd .', { cwd: projectDir });
237
+ // Remove node_modules and dist (.gitignore'd and therefore not removed via git clean)
238
+ (0, node_child_process_1.execSync)('rm -rf node_modules', { cwd: projectDir });
239
+ (0, node_child_process_1.execSync)('rm -rf dist', { cwd: projectDir });
229
240
  }
230
241
  catch (e) {
231
242
  exports.log.error('Error reverting local changes');
@@ -290,6 +301,20 @@ function modifyFile(filePath, replaceMap) {
290
301
  fs.writeFileSync(filePath, newFileContent);
291
302
  }
292
303
  exports.modifyFile = modifyFile;
304
+ /**
305
+ * Read the file contents and check if it does not contain the given content
306
+ *
307
+ * @param {string} filePath
308
+ * @param {(string | string[])} content
309
+ */
310
+ function checkFileDoesNotContain(filePath, content) {
311
+ const fileContent = fs.readFileSync(filePath, 'utf-8');
312
+ const contentArray = Array.isArray(content) ? content : [content];
313
+ for (const c of contentArray) {
314
+ (0, vitest_1.expect)(fileContent).not.toContain(c);
315
+ }
316
+ }
317
+ exports.checkFileDoesNotContain = checkFileDoesNotContain;
293
318
  /**
294
319
  * Read the file contents and check if it contains the given content
295
320
  *