Skip to content

Commit be8f194

Browse files
dashedmarkstory
authored andcommitted
feat(discover2): Discover v2 table and friends (#14403)
Remove hardcoded view data and support URL based queries, aggregates and tag lists. Refs SEN-907
1 parent 7453a86 commit be8f194

20 files changed

+1001
-560
lines changed

src/sentry/static/sentry/app/types/index.tsx

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -275,18 +275,14 @@ export type Group = {
275275
seenBy: User[];
276276
};
277277

278-
export type EventView = {
278+
export type EventViewv1 = {
279279
id: string;
280280
name: string;
281281
data: {
282282
fields: string[];
283283
columnNames: string[];
284284
sort: string[];
285285
query?: string;
286-
287-
// TODO: removed as of https://github.com/getsentry/sentry/pull/14321
288-
// groupby: string[];
289-
// orderby: string[];
290286
};
291287
tags: string[];
292288
columnWidths: string[];

src/sentry/static/sentry/app/views/organizationEventsV2/data.tsx

Lines changed: 74 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import React from 'react';
22
import styled from 'react-emotion';
3+
import {Location} from 'history';
34

4-
import {deepFreeze} from 'app/utils';
55
import {t} from 'app/locale';
66
import Count from 'app/components/count';
77
import DateTime from 'app/components/dateTime';
@@ -12,37 +12,28 @@ import getDynamicText from 'app/utils/getDynamicText';
1212
import overflowEllipsis from 'app/styles/overflowEllipsis';
1313
import pinIcon from 'app/../images/location-pin.png';
1414
import space from 'app/styles/space';
15-
import {EventView} from 'app/types';
15+
import {EventViewv1, Organization} from 'app/types';
1616

1717
import {QueryLink} from './styles';
1818

19-
// TODO(ts): add as const after babel upgrade
20-
export const MODAL_QUERY_KEYS = ['eventSlug'];
19+
export const MODAL_QUERY_KEYS = ['eventSlug'] as const;
2120
export const PIN_ICON = `image://${pinIcon}`;
22-
// TODO(ts): add as const after babel upgrade
23-
export const AGGREGATE_ALIASES = ['last_seen', 'latest_event'];
21+
export const AGGREGATE_ALIASES = ['last_seen', 'latest_event'] as const;
2422

25-
// TODO(ts): eventually defer to TS compile-time check to ensure this is readonly instead
26-
// of deepfreezing it in runtime
27-
export const ALL_VIEWS: Readonly<Array<EventView>> = deepFreeze([
28-
{
29-
id: 'all',
30-
name: t('All Events'),
31-
data: {
32-
fields: ['title', 'event.type', 'project', 'user', 'timestamp'],
33-
columnNames: ['title', 'type', 'project', 'user', 'time'],
34-
sort: ['-timestamp'],
35-
},
36-
tags: [
37-
'event.type',
38-
'release',
39-
'project.name',
40-
'user.email',
41-
'user.ip',
42-
'environment',
43-
],
44-
columnWidths: ['3fr', '80px', '1fr', '1fr', '1.5fr'],
23+
export const DEFAULT_EVENT_VIEW_V1: Readonly<EventViewv1> = {
24+
id: 'all',
25+
name: t('All Events'),
26+
data: {
27+
fields: ['title', 'event.type', 'project', 'user', 'timestamp'],
28+
columnNames: ['title', 'type', 'project', 'user', 'time'],
29+
sort: ['-timestamp'],
4530
},
31+
tags: ['event.type', 'release', 'project.name', 'user.email', 'user.ip', 'environment'],
32+
columnWidths: ['3fr', '80px', '1fr', '1fr', '1.5fr'],
33+
};
34+
35+
export const ALL_VIEWS: Readonly<Array<EventViewv1>> = [
36+
DEFAULT_EVENT_VIEW_V1,
4637
{
4738
id: 'errors',
4839
name: t('Errors'),
@@ -92,14 +83,47 @@ export const ALL_VIEWS: Readonly<Array<EventView>> = deepFreeze([
9283
],
9384
columnWidths: ['3fr', '1fr', '70px'],
9485
},
95-
]);
86+
];
87+
88+
type EventData = {[key: string]: any};
89+
90+
type RenderFunctionBaggage = {
91+
organization: Organization;
92+
location: Location;
93+
};
94+
95+
type FieldFormatterRenderFunction = (
96+
field: string,
97+
data: EventData,
98+
baggage: RenderFunctionBaggage
99+
) => React.ReactNode;
100+
101+
export type FieldFormatterRenderFunctionPartial = (
102+
data: EventData,
103+
baggage: RenderFunctionBaggage
104+
) => React.ReactNode;
105+
106+
type FieldFormatter = {
107+
sortField: boolean;
108+
renderFunc: FieldFormatterRenderFunction;
109+
};
110+
111+
type FieldFormatters = {
112+
boolean: FieldFormatter;
113+
integer: FieldFormatter;
114+
number: FieldFormatter;
115+
date: FieldFormatter;
116+
string: FieldFormatter;
117+
};
118+
119+
export type FieldTypes = keyof FieldFormatters;
96120

97121
/**
98122
* A mapping of field types to their rendering function.
99123
* This mapping is used when a field is not defined in SPECIAL_FIELDS
100124
* This mapping should match the output sentry.utils.snuba:get_json_type
101125
*/
102-
export const FIELD_FORMATTERS = {
126+
export const FIELD_FORMATTERS: FieldFormatters = {
103127
boolean: {
104128
sortField: true,
105129
renderFunc: (field, data, {organization, location}) => {
@@ -160,12 +184,31 @@ export const FIELD_FORMATTERS = {
160184
},
161185
};
162186

187+
type SpecialFieldRenderFunc = (
188+
data: EventData,
189+
baggage: RenderFunctionBaggage
190+
) => React.ReactNode;
191+
192+
type SpecialField = {
193+
sortField: string | null;
194+
renderFunc: SpecialFieldRenderFunc;
195+
};
196+
197+
type SpecialFields = {
198+
transaction: SpecialField;
199+
title: SpecialField;
200+
'event.type': SpecialField;
201+
project: SpecialField;
202+
user: SpecialField;
203+
last_seen: SpecialField;
204+
};
205+
163206
/**
164207
* "Special fields" do not map 1:1 to an single column in the event database,
165208
* they are a UI concept that combines the results of multiple fields and
166209
* displays with a custom render function.
167210
*/
168-
export const SPECIAL_FIELDS = {
211+
export const SPECIAL_FIELDS: SpecialFields = {
169212
transaction: {
170213
sortField: 'transaction',
171214
renderFunc: (data, {location}) => {
@@ -203,7 +246,7 @@ export const SPECIAL_FIELDS = {
203246
);
204247
},
205248
},
206-
type: {
249+
'event.type': {
207250
sortField: 'event.type',
208251
renderFunc: (data, {location}) => {
209252
const target = {
@@ -218,7 +261,7 @@ export const SPECIAL_FIELDS = {
218261
},
219262
},
220263
project: {
221-
sortField: false,
264+
sortField: null,
222265
renderFunc: (data, {organization}) => {
223266
const project = organization.projects.find(p => p.slug === data['project.name']);
224267
return (

0 commit comments

Comments
 (0)