projectReplays.tsx 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. import type {RouteComponentProps} from 'react-router';
  2. import Access from 'sentry/components/acl/access';
  3. import {LinkButton} from 'sentry/components/button';
  4. import Form from 'sentry/components/forms/form';
  5. import JsonForm from 'sentry/components/forms/jsonForm';
  6. import type {JsonFormObject} from 'sentry/components/forms/types';
  7. import Link from 'sentry/components/links/link';
  8. import ReplaySettingsAlert from 'sentry/components/replays/alerts/replaySettingsAlert';
  9. import SentryDocumentTitle from 'sentry/components/sentryDocumentTitle';
  10. import {t, tct} from 'sentry/locale';
  11. import type {Organization} from 'sentry/types/organization';
  12. import type {Project} from 'sentry/types/project';
  13. import SettingsPageHeader from 'sentry/views/settings/components/settingsPageHeader';
  14. import PermissionAlert from 'sentry/views/settings/project/permissionAlert';
  15. type RouteParams = {
  16. projectId: string;
  17. };
  18. type Props = RouteComponentProps<RouteParams, {}> & {
  19. organization: Organization;
  20. project: Project;
  21. };
  22. function ProjectReplaySettings({organization, project, params: {projectId}}: Props) {
  23. const formGroups: JsonFormObject[] = [
  24. {
  25. title: 'Settings',
  26. fields: [
  27. {
  28. name: 'sentry:replay_rage_click_issues',
  29. type: 'boolean',
  30. // additional data/props that is related to rendering of form field rather than data
  31. label: t('Create Rage Click Issues'),
  32. help: t('Toggles whether or not to create Session Replay Rage Click Issues'),
  33. getData: data => ({options: data}),
  34. },
  35. {
  36. name: 'sentry:replay_hydration_error_issues',
  37. type: 'boolean',
  38. // additional data/props that is related to rendering of form field rather than data
  39. label: t('Create Hydration Error Issues'),
  40. help() {
  41. return tct(
  42. 'Toggles whether or not to create Session Replay Hydration Error Issues during replay ingest. Using [inboundFilters: inbound filters] to filter out hydration errors does not affect this setting.',
  43. {
  44. inboundFilters: (
  45. <Link
  46. to={`/settings/projects/${project.slug}/filters/data-filters/#filters-react-hydration-errors_help`}
  47. />
  48. ),
  49. }
  50. );
  51. },
  52. getData: data => ({options: data}),
  53. visible({features}) {
  54. return features.has('session-replay-hydration-error-issue-creation');
  55. },
  56. },
  57. ],
  58. },
  59. ];
  60. return (
  61. <SentryDocumentTitle title={t('Replays')} projectSlug={project.slug}>
  62. <SettingsPageHeader
  63. title={t('Replays')}
  64. action={
  65. <LinkButton
  66. external
  67. href="https://docs.sentry.io/product/session-replay/replay-page-and-filters/"
  68. >
  69. {t('Read the Docs')}
  70. </LinkButton>
  71. }
  72. />
  73. <PermissionAlert project={project} />
  74. <ReplaySettingsAlert />
  75. <Form
  76. saveOnBlur
  77. apiMethod="PUT"
  78. apiEndpoint={`/projects/${organization.slug}/${projectId}/`}
  79. initialData={project.options}
  80. >
  81. <Access access={['project:write']} project={project}>
  82. {({hasAccess}) => (
  83. <JsonForm
  84. disabled={!hasAccess}
  85. features={new Set(organization.features)}
  86. forms={formGroups}
  87. />
  88. )}
  89. </Access>
  90. </Form>
  91. </SentryDocumentTitle>
  92. );
  93. }
  94. export default ProjectReplaySettings;