traceTable.tsx 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347
  1. import styled from '@emotion/styled';
  2. import {Tooltip} from 'sentry/components/tooltip';
  3. import {t} from 'sentry/locale';
  4. import {space} from 'sentry/styles/space';
  5. import EventView from 'sentry/utils/discover/eventView';
  6. import {useLocation} from 'sentry/utils/useLocation';
  7. import useOrganization from 'sentry/utils/useOrganization';
  8. import {
  9. generateProfileLink,
  10. generateReplayLink,
  11. generateTraceLink,
  12. generateTransactionLink,
  13. } from 'sentry/views/performance/transactionSummary/utils';
  14. import TransactionsTable from '../../components/discover/transactionsTable';
  15. // TODO(ddm): This is a placeholder component. Shown data is bogus.
  16. export function TraceTable() {
  17. const location = useLocation();
  18. const organization = useOrganization();
  19. const eventView = EventView.fromLocation(location);
  20. const tableData: any = {
  21. data: [
  22. {
  23. 'profile.id': null,
  24. timestamp: '2023-10-30T07:04:57+00:00',
  25. 'spans.ui': 4817.500354,
  26. 'span_ops_breakdown.relative': '',
  27. replayId: '2a3ef28213b2f408ca2828b6a27149c2b',
  28. 'transaction.duration': 11893,
  29. 'spans.db': null,
  30. trace: '9fe2707d6a4dc45efa75439764f963188a',
  31. 'spans.http': 8814.999819,
  32. 'spans.resource': 2655.700206,
  33. id: 'ddb209c68a54846b19e3422309afb26ca3',
  34. 'user.display': 'alexandra.cota@sentry.io',
  35. 'spans.browser': 637.500286,
  36. 'project.name': 'javascript',
  37. },
  38. {
  39. 'profile.id': '2a3ef28213b2f408ca2828b6a27149c2b',
  40. timestamp: '2023-10-29T22:17:08+00:00',
  41. 'spans.ui': 1985.199929,
  42. 'span_ops_breakdown.relative': '',
  43. replayId: '',
  44. 'transaction.duration': 11888,
  45. 'spans.db': null,
  46. trace: '343267d658554f44be28a42e49f460f3',
  47. 'spans.http': 9248.399973,
  48. 'spans.resource': 1555.999995,
  49. id: 'e77387c5a7e043312aaaf7f406c6049a2',
  50. 'user.display': 'matej.minar@sentry.io',
  51. 'spans.browser': 534.999848,
  52. 'project.name': 'javascript',
  53. },
  54. {
  55. 'profile.id': null,
  56. timestamp: '2023-10-30T01:45:19+00:00',
  57. 'spans.ui': 5709.600449,
  58. 'span_ops_breakdown.relative': '',
  59. replayId: '',
  60. 'transaction.duration': 11863,
  61. 'spans.db': null,
  62. trace: '9ad958c8af21d4c0db58bb5542c41c4d13',
  63. 'spans.http': 9214.499951,
  64. 'spans.resource': 2082.90124,
  65. id: 'acc1854b13a04f84bd2f0fc5b803dd65',
  66. 'user.display': 'riccardo.busetti@sentry.io',
  67. 'spans.browser': 389.699936,
  68. 'project.name': 'javascript',
  69. },
  70. {
  71. 'profile.id': '2a3ef28213b2f408ca2828b6a27149c2b',
  72. timestamp: '2023-10-29T16:59:16+00:00',
  73. 'spans.ui': 2638.000251,
  74. 'span_ops_breakdown.relative': '',
  75. replayId: '',
  76. 'transaction.duration': 11857,
  77. 'spans.db': null,
  78. trace: '548f0e7a4bd44a28aee52b890698440e',
  79. 'spans.http': 10524.60003,
  80. 'spans.resource': 222.597839,
  81. id: 'e491bd2be0734357ab9dcc690133a43b',
  82. 'user.display': 'ognjen.bostjancic@sentry.io',
  83. 'spans.browser': 877.500056,
  84. 'project.name': 'javascript',
  85. },
  86. {
  87. 'profile.id': null,
  88. timestamp: '2023-10-30T11:39:40+00:00',
  89. 'spans.ui': 2214.000223,
  90. 'span_ops_breakdown.relative': '',
  91. replayId: '2a3ef28213b2f408ca2828b6a27149c2b',
  92. 'transaction.duration': 11852,
  93. 'spans.db': null,
  94. trace: 'eaad797b3c2c34b79bb705e5af2db688b',
  95. 'spans.http': 4308.000088,
  96. 'spans.resource': 6362.000228,
  97. id: 'd53b10ef8edc43023b92caf8d0a8a473d',
  98. 'user.display': 'arhur.knaus@sentry.io',
  99. 'spans.browser': 615.000009,
  100. 'project.name': 'javascript',
  101. },
  102. ],
  103. meta: {
  104. 'profile.id': 'string',
  105. timestamp: 'date',
  106. 'spans.ui': 'duration',
  107. 'span_ops_breakdown.relative': 'string',
  108. replayId: 'string',
  109. 'transaction.duration': 'duration',
  110. 'spans.db': 'duration',
  111. trace: 'string',
  112. 'spans.http': 'duration',
  113. 'spans.resource': 'duration',
  114. id: 'string',
  115. 'user.display': 'string',
  116. 'spans.browser': 'duration',
  117. 'project.name': 'string',
  118. units: {
  119. 'profile.id': null,
  120. timestamp: null,
  121. 'spans.ui': 'millisecond',
  122. 'span_ops_breakdown.relative': null,
  123. replayId: null,
  124. 'transaction.duration': 'millisecond',
  125. 'spans.db': 'millisecond',
  126. trace: null,
  127. 'spans.http': 'millisecond',
  128. 'spans.resource': 'millisecond',
  129. id: null,
  130. 'user.display': null,
  131. 'spans.browser': 'millisecond',
  132. 'project.name': null,
  133. },
  134. isMetricsData: false,
  135. tips: {
  136. query: null,
  137. columns: null,
  138. },
  139. datasetReason: 'unchanged',
  140. dataset: 'discover',
  141. },
  142. };
  143. const columnOrder: any = [
  144. {
  145. key: 'id',
  146. name: 'id',
  147. type: 'string',
  148. isSortable: false,
  149. column: {
  150. kind: 'field',
  151. field: 'id',
  152. },
  153. width: -1,
  154. },
  155. {
  156. key: 'user.display',
  157. name: 'user.display',
  158. type: 'string',
  159. isSortable: false,
  160. column: {
  161. kind: 'field',
  162. field: 'user.display',
  163. },
  164. width: -1,
  165. },
  166. {
  167. key: 'span_ops_breakdown.relative',
  168. name: 'span_ops_breakdown.relative',
  169. type: 'never',
  170. isSortable: false,
  171. column: {
  172. kind: 'field',
  173. field: 'span_ops_breakdown.relative',
  174. },
  175. width: -1,
  176. },
  177. {
  178. key: 'transaction.duration',
  179. name: 'transaction.duration',
  180. type: 'duration',
  181. isSortable: false,
  182. column: {
  183. kind: 'field',
  184. field: 'transaction.duration',
  185. },
  186. width: -1,
  187. },
  188. {
  189. key: 'trace',
  190. name: 'trace',
  191. type: 'string',
  192. isSortable: false,
  193. column: {
  194. kind: 'field',
  195. field: 'trace',
  196. },
  197. width: -1,
  198. },
  199. {
  200. key: 'timestamp',
  201. name: 'timestamp',
  202. type: 'date',
  203. isSortable: false,
  204. column: {
  205. kind: 'field',
  206. field: 'timestamp',
  207. },
  208. width: -1,
  209. },
  210. {
  211. key: 'replayId',
  212. name: 'replayId',
  213. type: 'string',
  214. isSortable: false,
  215. column: {
  216. kind: 'field',
  217. field: 'replayId',
  218. },
  219. width: -1,
  220. },
  221. {
  222. key: 'profile.id',
  223. name: 'profile.id',
  224. type: 'string',
  225. isSortable: false,
  226. column: {
  227. kind: 'field',
  228. field: 'profile.id',
  229. },
  230. width: -1,
  231. },
  232. {
  233. key: 'spans.browser',
  234. name: 'spans.browser',
  235. type: 'duration',
  236. isSortable: false,
  237. column: {
  238. kind: 'field',
  239. field: 'spans.browser',
  240. },
  241. width: -1,
  242. },
  243. {
  244. key: 'spans.db',
  245. name: 'spans.db',
  246. type: 'duration',
  247. isSortable: false,
  248. column: {
  249. kind: 'field',
  250. field: 'spans.db',
  251. },
  252. width: -1,
  253. },
  254. {
  255. key: 'spans.http',
  256. name: 'spans.http',
  257. type: 'duration',
  258. isSortable: false,
  259. column: {
  260. kind: 'field',
  261. field: 'spans.http',
  262. },
  263. width: -1,
  264. },
  265. {
  266. key: 'spans.resource',
  267. name: 'spans.resource',
  268. type: 'duration',
  269. isSortable: false,
  270. column: {
  271. kind: 'field',
  272. field: 'spans.resource',
  273. },
  274. width: -1,
  275. },
  276. {
  277. key: 'spans.ui',
  278. name: 'spans.ui',
  279. type: 'duration',
  280. isSortable: false,
  281. column: {
  282. kind: 'field',
  283. field: 'spans.ui',
  284. },
  285. width: -1,
  286. },
  287. ];
  288. const widgetsQuery = JSON.parse((location?.query?.widgets as string) ?? '[]');
  289. const hasSelectedMris = widgetsQuery.filter(w => w.mri);
  290. if (!hasSelectedMris.length) {
  291. return null;
  292. }
  293. return (
  294. <TraceTableWrapper>
  295. <Tooltip title={t('Coming soon. This is where you will see samples.')}>
  296. <TransactionsTable
  297. eventView={eventView}
  298. organization={organization}
  299. location={location}
  300. isLoading={false}
  301. tableData={tableData}
  302. columnOrder={columnOrder}
  303. titles={[
  304. 'event id',
  305. 'user',
  306. 'operation duration',
  307. 'total duration',
  308. 'trace id',
  309. 'timestamp',
  310. 'replay',
  311. 'profile',
  312. ]}
  313. generateLink={{
  314. id: generateTransactionLink(''),
  315. trace: generateTraceLink(eventView.normalizeDateSelection(location)),
  316. replayId: generateReplayLink([]),
  317. 'profile.id': generateProfileLink(),
  318. }}
  319. useAggregateAlias
  320. />
  321. </Tooltip>
  322. </TraceTableWrapper>
  323. );
  324. }
  325. const TraceTableWrapper = styled('div')`
  326. margin-top: ${space(3)};
  327. filter: blur(3px);
  328. width: 100%;
  329. user-select: none;
  330. > span {
  331. width: 100%;
  332. }
  333. > span > div {
  334. pointer-events: none;
  335. }
  336. `;