Browse Source

feat(replay): Request data from the a11y service (#57423)

Relates to https://github.com/getsentry/sentry/issues/55293
Ryan Albrecht 1 year ago
parent
commit
dfb251926e

+ 30 - 0
static/app/utils/replays/hooks/useA11yData.tsx

@@ -0,0 +1,30 @@
+import {useReplayContext} from 'sentry/components/replays/replayContext';
+import {useApiQuery} from 'sentry/utils/queryClient';
+import hydrateA11yIssue, {A11yIssue} from 'sentry/utils/replays/hydrateA11yRecord';
+import useOrganization from 'sentry/utils/useOrganization';
+import useProjects from 'sentry/utils/useProjects';
+
+export default function useA11yData() {
+  const organization = useOrganization();
+  const {replay} = useReplayContext();
+  const {projects} = useProjects();
+
+  const replayRecord = replay?.getReplay();
+  const startTimestampMs = replayRecord?.started_at.getTime();
+  const project = projects.find(p => p.id === replayRecord?.project_id);
+
+  const {data} = useApiQuery<A11yIssue[]>(
+    [
+      `/projects/${organization.slug}/${project?.slug}/replays/${replayRecord?.id}/accessibility-issues/`,
+    ],
+    {
+      staleTime: 0,
+      enabled: Boolean(project) && Boolean(replayRecord),
+    }
+  );
+
+  if (project && replayRecord && startTimestampMs) {
+    return data?.map(record => hydrateA11yIssue(record, startTimestampMs));
+  }
+  return [];
+}

+ 52 - 0
static/app/utils/replays/hydrateA11yRecord.tsx

@@ -0,0 +1,52 @@
+export interface A11yIssue {
+  elements: A11yIssueElement[];
+  help: string;
+  help_url: string;
+  id: string;
+  timestamp: number;
+  impact?: 'minor' | 'moderate' | 'serious' | 'critical';
+}
+
+interface A11yIssueElement {
+  alternatives: A11yIssueElementAlternative[];
+  element: string;
+  target: string[];
+}
+
+interface A11yIssueElementAlternative {
+  id: string;
+  message: string;
+}
+
+type Overwrite<T, U> = Pick<T, Exclude<keyof T, keyof U>> & U;
+
+export type HydratedA11yIssue = Overwrite<
+  A11yIssue,
+  {
+    /**
+     * The difference in timestamp and replay.started_at, in millieseconds
+     */
+    offsetMs: number;
+    /**
+     * The Date when the breadcrumb happened
+     */
+    timestamp: Date;
+    /**
+     * Alias of timestamp, in milliseconds
+     */
+    timestampMs: number;
+  }
+>;
+
+export default function hydrateA11yIssue(
+  raw: A11yIssue,
+  startTimestampMs: number
+): HydratedA11yIssue {
+  const timestamp = new Date(raw.timestamp);
+  return {
+    ...raw,
+    offsetMs: 0,
+    timestamp,
+    timestampMs: Math.abs(timestamp.getTime() - startTimestampMs),
+  };
+}

+ 6 - 0
static/app/views/replays/detail/accessibility/index.tsx

@@ -1,6 +1,12 @@
+import useA11yData from 'sentry/utils/replays/hooks/useA11yData';
+
 type Props = {};
 
 function A11y({}: Props) {
+  const data = useA11yData();
+  // eslint-disable-next-line no-console
+  console.log(data);
+
   return <div />;
 }