0 })}
+ >
- setShowEvents(data.length > 0)} />
+
-
diff --git a/components/common/ButtonGroup.module.css b/components/common/ButtonGroup.module.css
index b93189e5..d18a8e9c 100644
--- a/components/common/ButtonGroup.module.css
+++ b/components/common/ButtonGroup.module.css
@@ -2,13 +2,13 @@
display: inline-flex;
border-radius: 4px;
overflow: hidden;
- border: 1px solid var(--gray400);
+ border: 1px solid var(--gray500);
}
.group .button {
border-radius: 0;
background: var(--gray50);
- border-left: 1px solid var(--gray400);
+ border-left: 1px solid var(--gray500);
padding: 4px 8px;
}
@@ -16,6 +16,10 @@
border: 0;
}
+.group .button:hover {
+ background: var(--gray100);
+}
+
.group .button + .button {
margin: 0;
}
diff --git a/components/metrics/BarChart.js b/components/metrics/BarChart.js
index e3853b0d..fdce6330 100644
--- a/components/metrics/BarChart.js
+++ b/components/metrics/BarChart.js
@@ -2,7 +2,7 @@ import React, { useState, useRef, useEffect } from 'react';
import ReactTooltip from 'react-tooltip';
import classNames from 'classnames';
import ChartJS from 'chart.js';
-import styles from './PageviewsChart.module.css';
+import styles from './BarChart.module.css';
import { format } from 'date-fns';
export default function BarChart({
@@ -10,6 +10,7 @@ export default function BarChart({
datasets,
unit,
records,
+ height = 400,
animationDuration = 300,
className,
stacked = false,
@@ -68,7 +69,9 @@ export default function BarChart({
hover: {
animationDuration: 0,
},
+ responsive: true,
responsiveAnimationDuration: 0,
+ maintainAspectRatio: false,
scales: {
xAxes: [
{
@@ -133,16 +136,19 @@ export default function BarChart({
}, [datasets]);
return (
-
-
+ <>
+
+
+
{tooltip ? : null}
-
+ >
);
}
diff --git a/components/metrics/PageviewsChart.module.css b/components/metrics/BarChart.module.css
similarity index 100%
rename from components/metrics/PageviewsChart.module.css
rename to components/metrics/BarChart.module.css
diff --git a/components/metrics/EventsChart.js b/components/metrics/EventsChart.js
index 6400539a..1825116f 100644
--- a/components/metrics/EventsChart.js
+++ b/components/metrics/EventsChart.js
@@ -1,33 +1,38 @@
import React, { useState, useEffect, useMemo } from 'react';
import classNames from 'classnames';
+import tinycolor from 'tinycolor2';
import BarChart from './BarChart';
import { get } from 'lib/web';
import { getTimezone, getDateArray, getDateLength } from 'lib/date';
-import styles from './PageviewsChart.module.css';
+import styles from './BarChart.module.css';
const COLORS = [
- 'rgba(38, 128, 235, 0.5)',
- 'rgba(146, 86, 217, 0.5)',
- 'rgba(45, 157, 120, 0.5)',
- 'rgba(216, 55, 144, 0.5)',
- 'rgba(227, 72, 80, 0.5)',
- 'rgba(103, 103, 236, 0.5)',
- 'rgba(68, 181, 86, 0.5)',
+ '#2680eb',
+ '#9256d9',
+ '#44b556',
+ '#e68619',
+ '#e34850',
+ '#1b959a',
+ '#d83790',
+ '#85d044',
];
-export default function EventsChart({ websiteId, startDate, endDate, unit, className }) {
+export default function EventsChart({ websiteId, startDate, endDate, unit }) {
const [data, setData] = useState();
const datasets = useMemo(() => {
if (!data) return [];
- return Object.keys(data).map((key, index) => ({
- label: key,
- data: data[key],
- lineTension: 0,
- backgroundColor: COLORS[index],
- borderColor: COLORS[index],
- borderWidth: 1,
- }));
+ return Object.keys(data).map((key, index) => {
+ const color = tinycolor(COLORS[index]);
+ return {
+ label: key,
+ data: data[key],
+ lineTension: 0,
+ backgroundColor: color.setAlpha(0.4).toRgbString(),
+ borderColor: color.setAlpha(0.5).toRgbString(),
+ borderWidth: 1,
+ };
+ });
}, [data]);
async function loadData() {
@@ -55,6 +60,14 @@ export default function EventsChart({ websiteId, startDate, endDate, unit, class
setData(map);
}
+ function handleCreate(options) {
+ const legend = {
+ position: 'bottom',
+ };
+
+ options.legend = legend;
+ }
+
function handleUpdate(chart) {
chart.data.datasets = datasets;
@@ -70,15 +83,14 @@ export default function EventsChart({ websiteId, startDate, endDate, unit, class
}
return (
-
-
-
+
);
}
diff --git a/components/metrics/EventsTable.js b/components/metrics/EventsTable.js
index 9110bfb8..91e5a401 100644
--- a/components/metrics/EventsTable.js
+++ b/components/metrics/EventsTable.js
@@ -2,7 +2,7 @@ import React from 'react';
import MetricsTable from './MetricsTable';
import styles from './EventsTable.module.css';
-export default function DevicesTable({
+export default function EventsTable({
websiteId,
startDate,
endDate,
@@ -19,14 +19,19 @@ export default function DevicesTable({
startDate={startDate}
endDate={endDate}
limit={limit}
- renderLabel={({ w, x }) => (
- <>
-
{w}
- {x}
- >
- )}
+ renderLabel={({ x }) =>
}
onExpand={onExpand}
onDataLoad={onDataLoad}
/>
);
}
+
+const Label = ({ value }) => {
+ const [event, label] = value.split(':');
+ return (
+ <>
+
{event}
+ {label}
+ >
+ );
+};
diff --git a/components/metrics/PageviewsChart.js b/components/metrics/PageviewsChart.js
index d810acf3..1052452b 100644
--- a/components/metrics/PageviewsChart.js
+++ b/components/metrics/PageviewsChart.js
@@ -1,7 +1,5 @@
import React from 'react';
-import classNames from 'classnames';
import BarChart from './BarChart';
-import styles from './PageviewsChart.module.css';
export default function PageviewsChart({ websiteId, data, unit, className, animationDuration }) {
const handleUpdate = chart => {
@@ -22,31 +20,30 @@ export default function PageviewsChart({ websiteId, data, unit, className, anima
}
return (
-
-
-
+
);
}
diff --git a/lib/queries.js b/lib/queries.js
index 592ae85c..1907a954 100644
--- a/lib/queries.js
+++ b/lib/queries.js
@@ -401,44 +401,6 @@ export function getActiveVisitors(website_id) {
return Promise.resolve([]);
}
-export function getEventRankings(website_id, start_at, end_at) {
- const db = getDatabase();
-
- if (db === POSTGRESQL) {
- return prisma.$queryRaw(
- `
- select distinct event_type w, event_value x, count(*) y
- from event
- where website_id=$1
- and created_at between $2 and $3
- group by 1, 2
- order by 3 desc
- `,
- website_id,
- start_at,
- end_at,
- );
- }
-
- if (db === MYSQL) {
- return prisma.$queryRaw(
- `
- select distinct event_type w, event_value x, count(*) y
- from event
- where website_id=?
- and created_at between ? and ?
- group by 1, 2
- order by 3 desc
- `,
- website_id,
- start_at,
- end_at,
- );
- }
-
- return Promise.resolve([]);
-}
-
export function getEvents(website_id, start_at, end_at, timezone = 'utc', unit = 'day') {
const db = getDatabase();
diff --git a/pages/api/website/[id]/rankings.js b/pages/api/website/[id]/rankings.js
index 9c742390..8d1d95bf 100644
--- a/pages/api/website/[id]/rankings.js
+++ b/pages/api/website/[id]/rankings.js
@@ -1,9 +1,28 @@
-import { getRankings, getEventRankings } from 'lib/queries';
+import { getRankings } from 'lib/queries';
import { ok, badRequest } from 'lib/response';
const sessionColumns = ['browser', 'os', 'device', 'country'];
const pageviewColumns = ['url', 'referrer'];
+function getTable(type) {
+ if (type === 'event') {
+ return 'event';
+ }
+
+ if (sessionColumns.includes(type)) {
+ return 'session';
+ }
+
+ return 'pageview';
+}
+
+function getColumn(type) {
+ if (type === 'event') {
+ return `concat(event_type, ':', event_value)`;
+ }
+ return type;
+}
+
export default async (req, res) => {
const { id, type, start_at, end_at } = req.query;
const websiteId = +id;
@@ -14,15 +33,13 @@ export default async (req, res) => {
return badRequest(res);
}
- if (type === 'event') {
- const events = await getEventRankings(websiteId, startDate, endDate);
-
- return ok(res, events);
- }
-
- const table = sessionColumns.includes(type) ? 'session' : 'pageview';
-
- const rankings = await getRankings(websiteId, startDate, endDate, type, table);
+ const rankings = await getRankings(
+ websiteId,
+ startDate,
+ endDate,
+ getColumn(type),
+ getTable(type),
+ );
return ok(res, rankings);
};