express.tsx 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187
  1. import {Layout, LayoutProps} from 'sentry/components/onboarding/gettingStartedDoc/layout';
  2. import {ModuleProps} from 'sentry/components/onboarding/gettingStartedDoc/sdkDocumentation';
  3. import {StepProps, StepType} from 'sentry/components/onboarding/gettingStartedDoc/step';
  4. import {getUploadSourceMapsStep} from 'sentry/components/onboarding/gettingStartedDoc/utils';
  5. import {t, tct} from 'sentry/locale';
  6. import {
  7. getDefaultInitParams,
  8. getDefaultNodeImports,
  9. getInstallSnippet,
  10. getProductInitParams,
  11. getProductIntegrations,
  12. getProductSelectionMap,
  13. joinWithIndentation,
  14. } from 'sentry/utils/gettingStartedDocs/node';
  15. interface StepsParams {
  16. hasPerformanceMonitoring: boolean;
  17. importContent: string;
  18. initContent: string;
  19. installSnippetNpm: string;
  20. installSnippetYarn: string;
  21. sourceMapStep: StepProps;
  22. }
  23. const performanceIntegrations: string[] = [
  24. '// enable HTTP calls tracing',
  25. 'new Sentry.Integrations.Http({ tracing: true }),',
  26. '// enable Express.js middleware tracing',
  27. 'new Sentry.Integrations.Express({ app }),',
  28. ];
  29. export const steps = ({
  30. installSnippetYarn,
  31. installSnippetNpm,
  32. importContent,
  33. initContent,
  34. hasPerformanceMonitoring,
  35. sourceMapStep,
  36. }: StepsParams): LayoutProps['steps'] => [
  37. {
  38. type: StepType.INSTALL,
  39. description: t('Add the Sentry Node SDK as a dependency:'),
  40. configurations: [
  41. {
  42. code: [
  43. {
  44. label: 'npm',
  45. value: 'npm',
  46. language: 'bash',
  47. code: installSnippetNpm,
  48. },
  49. {
  50. label: 'yarn',
  51. value: 'yarn',
  52. language: 'bash',
  53. code: installSnippetYarn,
  54. },
  55. ],
  56. },
  57. ],
  58. },
  59. {
  60. type: StepType.CONFIGURE,
  61. description: (
  62. <p>
  63. {tct(
  64. "Initialize Sentry as early as possible in your application's lifecycle, for example in your [code:index.ts/js] entry point:",
  65. {code: <code />}
  66. )}
  67. </p>
  68. ),
  69. configurations: [
  70. {
  71. language: 'javascript',
  72. code: `
  73. ${importContent}
  74. const app = express();
  75. Sentry.init({
  76. ${initContent}
  77. });
  78. // The request handler must be the first middleware on the app
  79. app.use(Sentry.Handlers.requestHandler());${
  80. hasPerformanceMonitoring
  81. ? `
  82. // TracingHandler creates a trace for every incoming request
  83. app.use(Sentry.Handlers.tracingHandler());`
  84. : ''
  85. }
  86. // All your controllers should live here
  87. app.get("/", function rootHandler(req, res) {
  88. res.end("Hello world!");
  89. });
  90. // The error handler must be registered before any other error middleware and after all controllers
  91. app.use(Sentry.Handlers.errorHandler());
  92. // Optional fallthrough error handler
  93. app.use(function onError(err, req, res, next) {
  94. // The error id is attached to \`res.sentry\` to be returned
  95. // and optionally displayed to the user for support.
  96. res.statusCode = 500;
  97. res.end(res.sentry + "\\n");
  98. });
  99. app.listen(3000);
  100. `,
  101. },
  102. ],
  103. },
  104. sourceMapStep,
  105. {
  106. type: StepType.VERIFY,
  107. description: t(
  108. "This snippet contains an intentional error and can be used as a test to make sure that everything's working as expected."
  109. ),
  110. configurations: [
  111. {
  112. language: 'javascript',
  113. code: `
  114. app.get("/debug-sentry", function mainHandler(req, res) {
  115. throw new Error("My first Sentry error!");
  116. });
  117. `,
  118. },
  119. ],
  120. },
  121. ];
  122. export function GettingStartedWithExpress({
  123. dsn,
  124. newOrg,
  125. platformKey,
  126. activeProductSelection = [],
  127. organization,
  128. projectId,
  129. ...props
  130. }: ModuleProps) {
  131. const productSelection = getProductSelectionMap(activeProductSelection);
  132. const imports = getDefaultNodeImports({productSelection});
  133. imports.push('import express from "express";');
  134. const integrations = [
  135. ...(productSelection['performance-monitoring'] ? performanceIntegrations : []),
  136. ...getProductIntegrations({productSelection}),
  137. ];
  138. const integrationParam =
  139. integrations.length > 0
  140. ? `integrations: [\n${joinWithIndentation(integrations)}\n],`
  141. : null;
  142. const initContent = joinWithIndentation([
  143. ...getDefaultInitParams({dsn}),
  144. ...(integrationParam ? [integrationParam] : []),
  145. ...getProductInitParams({productSelection}),
  146. ]);
  147. return (
  148. <Layout
  149. steps={steps({
  150. installSnippetNpm: getInstallSnippet({productSelection, packageManager: 'npm'}),
  151. installSnippetYarn: getInstallSnippet({productSelection, packageManager: 'yarn'}),
  152. importContent: imports.join('\n'),
  153. initContent,
  154. hasPerformanceMonitoring: productSelection['performance-monitoring'],
  155. sourceMapStep: getUploadSourceMapsStep({
  156. guideLink: 'https://docs.sentry.io/platforms/node/guides/express/sourcemaps/',
  157. organization,
  158. platformKey,
  159. projectId,
  160. newOrg,
  161. }),
  162. })}
  163. newOrg={newOrg}
  164. platformKey={platformKey}
  165. {...props}
  166. />
  167. );
  168. }
  169. export default GettingStartedWithExpress;