diff --git a/shynet/core/models.py b/shynet/core/models.py index 7a424e9..5d6f5a7 100644 --- a/shynet/core/models.py +++ b/shynet/core/models.py @@ -8,7 +8,7 @@ from django.conf import settings from django.contrib.auth.models import AbstractUser from django.core.exceptions import ValidationError from django.db import models -from django.db.models.functions import TruncDate +from django.db.models.functions import TruncDate, TruncHour from django.db.utils import NotSupportedError from django.shortcuts import reverse from django.utils import timezone @@ -125,8 +125,10 @@ class Service(models.Model): Session = apps.get_model("analytics", "Session") Hit = apps.get_model("analytics", "Hit") + tz_now = timezone.now() + currently_online = Session.objects.filter( - service=self, last_seen__gt=timezone.now() - ACTIVE_USER_TIMEDELTA + service=self, last_seen__gt=tz_now - ACTIVE_USER_TIMEDELTA ).count() sessions = Session.objects.filter( @@ -210,17 +212,35 @@ class Service(models.Model): if session_count == 0: avg_session_duration = None - session_chart_data = { - k["date"]: k["count"] - for k in sessions.annotate(date=TruncDate("start_time")) - .values("date") - .annotate(count=models.Count("uuid")) - .order_by("date") - } - for day_offset in range((end_time - start_time).days + 1): - day = (start_time + timezone.timedelta(days=day_offset)).date() - if day not in session_chart_data: - session_chart_data[day] = 0 + # Show hourly chart for date ranges of 3 days or less, otherwise daily chart + if (end_time - start_time).days < 3: + session_chart_tooltip_format = "MM/dd HH:mm" + session_chart_granularity = "hourly" + session_chart_data = { + k["hour"]: k["count"] + for k in sessions.annotate(hour=TruncHour("start_time")) + .values("hour") + .annotate(count=models.Count("uuid")) + .order_by("hour") + } + for hour_offset in range(int((end_time - start_time).total_seconds() / 3600) + 1): + hour = (start_time + timezone.timedelta(hours=hour_offset)) + if hour not in session_chart_data: + session_chart_data[hour] = 0 if hour <= tz_now else None + else: + session_chart_tooltip_format = "MMM d" + session_chart_granularity = "daily" + session_chart_data = { + k["date"]: k["count"] + for k in sessions.annotate(date=TruncDate("start_time")) + .values("date") + .annotate(count=models.Count("uuid")) + .order_by("date") + } + for day_offset in range((end_time - start_time).days + 1): + day = (start_time + timezone.timedelta(days=day_offset)).date() + if day not in session_chart_data: + session_chart_data[day] = 0 if day <= tz_now.date() else None return { "currently_online": currently_online, @@ -249,6 +269,8 @@ class Service(models.Model): ) ] ), + "session_chart_tooltip_format": session_chart_tooltip_format, + "session_chart_granularity": session_chart_granularity, "online": True, } diff --git a/shynet/dashboard/templates/dashboard/includes/service_overview.html b/shynet/dashboard/templates/dashboard/includes/service_overview.html index 8c4033a..1720413 100644 --- a/shynet/dashboard/templates/dashboard/includes/service_overview.html +++ b/shynet/dashboard/templates/dashboard/includes/service_overview.html @@ -51,7 +51,7 @@
- {% include 'dashboard/includes/time_chart.html' with data=stats.session_chart_data sparkline=True height=100 name=object.uuid %} + {% include 'dashboard/includes/time_chart.html' with data=stats.session_chart_data sparkline=True height=100 name=object.uuid tooltip_format=stats.session_chart_tooltip_format granularity=stats.session_chart_granularity %}
{% endwith %} \ No newline at end of file diff --git a/shynet/dashboard/templates/dashboard/includes/time_chart.html b/shynet/dashboard/templates/dashboard/includes/time_chart.html index 61e50ec..22542a9 100644 --- a/shynet/dashboard/templates/dashboard/includes/time_chart.html +++ b/shynet/dashboard/templates/dashboard/includes/time_chart.html @@ -6,6 +6,9 @@ }, tooltip: { shared: false, + x: { + format: '{{tooltip_format|default:"MMM d"}}', + }, }, colors: ["#805AD5"], chart: { @@ -34,6 +37,14 @@ stops: [0, 75, 100] }, }, + {% if granularity == "daily" and click_zoom %} + events: { + markerClick: function(event, chartContext, { seriesIndex, dataPointIndex, w: {config}}) { + const day = config.series[seriesIndex].data[dataPointIndex].x + window.location.href = `?startDate=${day}&endDate=${day}` + }, + }, + {% endif %} }, grid: { padding: { @@ -63,6 +74,9 @@ }, xaxis: { type: "datetime", + labels: { + datetimeUTC: false + }, }, stroke: { width: 1.5, diff --git a/shynet/dashboard/templates/dashboard/pages/service.html b/shynet/dashboard/templates/dashboard/pages/service.html index 28d58c1..d005b1b 100644 --- a/shynet/dashboard/templates/dashboard/pages/service.html +++ b/shynet/dashboard/templates/dashboard/pages/service.html @@ -94,7 +94,7 @@ {% endwith %}
- {% include 'dashboard/includes/time_chart.html' with data=stats.session_chart_data %} + {% include 'dashboard/includes/time_chart.html' with data=stats.session_chart_data tooltip_format=stats.session_chart_tooltip_format granularity=stats.session_chart_granularity click_zoom=True %}
{% endif %}