|
1 | 1 | import Button from "@material-ui/core/Button"
|
2 | 2 | import AddCircleOutline from "@material-ui/icons/AddCircleOutline"
|
| 3 | +import moment from "moment" |
3 | 4 | import { FC } from "react"
|
| 5 | +import { Line } from "react-chartjs-2" |
4 | 6 | import * as TypesGen from "../../api/typesGenerated"
|
5 | 7 | import { Margins } from "../../components/Margins/Margins"
|
6 | 8 | import { PageHeader, PageHeaderTitle } from "../../components/PageHeader/PageHeader"
|
7 | 9 | import { SearchBarWithFilter } from "../../components/SearchBarWithFilter/SearchBarWithFilter"
|
8 | 10 | import { UsersTable } from "../../components/UsersTable/UsersTable"
|
9 | 11 | import { userFilterQuery } from "../../util/filters"
|
10 |
| -import { DAUChart } from "./DAUChart" |
| 12 | + |
| 13 | +import useTheme from "@material-ui/styles/useTheme" |
| 14 | + |
| 15 | +import { Theme } from "@material-ui/core/styles" |
| 16 | +import { |
| 17 | + CategoryScale, |
| 18 | + Chart as ChartJS, |
| 19 | + ChartOptions, |
| 20 | + defaults, |
| 21 | + Legend, |
| 22 | + LinearScale, |
| 23 | + LineElement, |
| 24 | + PointElement, |
| 25 | + Title, |
| 26 | + Tooltip, |
| 27 | +} from "chart.js" |
| 28 | +import { Stack } from "components/Stack/Stack" |
| 29 | +import { HelpTooltip, HelpTooltipText, HelpTooltipTitle } from "components/Tooltips/HelpTooltip" |
| 30 | +import { WorkspaceSection } from "components/WorkspaceSection/WorkspaceSection" |
11 | 31 |
|
12 | 32 | export const Language = {
|
13 | 33 | pageTitle: "Users",
|
14 | 34 | createButton: "New user",
|
15 | 35 | activeUsersFilterName: "Active users",
|
16 | 36 | allUsersFilterName: "All users",
|
17 | 37 | }
|
| 38 | +ChartJS.register(CategoryScale, LinearScale, PointElement, LineElement, Title, Tooltip, Legend) |
| 39 | + |
| 40 | +export interface DAUChartProps { |
| 41 | + userMetricsData: TypesGen.DAUsResponse |
| 42 | +} |
| 43 | + |
| 44 | +export const DAUChart: FC<DAUChartProps> = ({ userMetricsData }) => { |
| 45 | + const theme: Theme = useTheme() |
| 46 | + |
| 47 | + if (userMetricsData.entries.length === 0) { |
| 48 | + return ( |
| 49 | + <div style={{ marginTop: "-20px" }}> |
| 50 | + <p>DAU stats are loading. Check back later.</p> |
| 51 | + </div> |
| 52 | + ) |
| 53 | + } |
| 54 | + |
| 55 | + const labels = userMetricsData.entries.map((val) => { |
| 56 | + return moment(val.date).format("l") |
| 57 | + }) |
| 58 | + |
| 59 | + const data = userMetricsData.entries.map((val) => { |
| 60 | + return val.daus |
| 61 | + }) |
| 62 | + |
| 63 | + defaults.font.family = theme.typography.fontFamily |
| 64 | + |
| 65 | + const options = { |
| 66 | + responsive: true, |
| 67 | + plugins: { |
| 68 | + legend: { |
| 69 | + display: false, |
| 70 | + }, |
| 71 | + }, |
| 72 | + scales: { |
| 73 | + y: { |
| 74 | + min: 0, |
| 75 | + ticks: { |
| 76 | + precision: 0, |
| 77 | + }, |
| 78 | + }, |
| 79 | + x: { |
| 80 | + ticks: {}, |
| 81 | + }, |
| 82 | + }, |
| 83 | + aspectRatio: 6 / 1, |
| 84 | + } as ChartOptions |
| 85 | + |
| 86 | + return ( |
| 87 | + <> |
| 88 | + {/* <WorkspaceSection title="Daily Active Users"> */} |
| 89 | + <WorkspaceSection> |
| 90 | + <Stack direction="row" spacing={1} alignItems="center"> |
| 91 | + <h3>Daily Active Users</h3> |
| 92 | + <HelpTooltip size="small"> |
| 93 | + <HelpTooltipTitle>How do we calculate DAUs?</HelpTooltipTitle> |
| 94 | + <HelpTooltipText> |
| 95 | + We use daily, unique workspace connection traffic to compute DAUs. |
| 96 | + </HelpTooltipText> |
| 97 | + </HelpTooltip> |
| 98 | + </Stack> |
| 99 | + <Line |
| 100 | + data={{ |
| 101 | + labels: labels, |
| 102 | + datasets: [ |
| 103 | + { |
| 104 | + label: "Daily Active Users", |
| 105 | + data: data, |
| 106 | + lineTension: 1 / 4, |
| 107 | + backgroundColor: theme.palette.secondary.dark, |
| 108 | + borderColor: theme.palette.secondary.dark, |
| 109 | + }, |
| 110 | + // There are type bugs in chart.js that force us to use any. |
| 111 | + // eslint-disable-next-line @typescript-eslint/no-explicit-any |
| 112 | + ] as any, |
| 113 | + }} |
| 114 | + // eslint-disable-next-line @typescript-eslint/no-explicit-any |
| 115 | + options={options as any} |
| 116 | + height={400} |
| 117 | + /> |
| 118 | + </WorkspaceSection> |
| 119 | + </> |
| 120 | + ) |
| 121 | +} |
18 | 122 |
|
19 | 123 | export interface UsersPageViewProps {
|
20 |
| - userMetricsData?: TypesGen.GetDAUsResponse |
| 124 | + userMetricsData?: TypesGen.DAUsResponse |
21 | 125 | users?: TypesGen.User[]
|
22 | 126 | roles?: TypesGen.AssignableRoles[]
|
23 | 127 | filter?: string
|
|
0 commit comments