migrate more

Signed-off-by: Jens Langhammer <jens@goauthentik.io>
This commit is contained in:
Jens Langhammer
2025-06-06 03:27:22 +02:00
parent abb9e13d27
commit eb63e22bf5
5 changed files with 26 additions and 54 deletions

View File

@ -1,6 +1,5 @@
"""authentik administration metrics""" """authentik administration metrics"""
from rest_framework.fields import IntegerField from rest_framework.fields import IntegerField
from authentik.core.api.utils import PassiveSerializer from authentik.core.api.utils import PassiveSerializer

View File

@ -2,11 +2,9 @@
from collections.abc import Iterator from collections.abc import Iterator
from copy import copy from copy import copy
from datetime import timedelta
from django.core.cache import cache from django.core.cache import cache
from django.db.models import QuerySet from django.db.models import QuerySet
from django.db.models.functions import ExtractHour
from django.shortcuts import get_object_or_404 from django.shortcuts import get_object_or_404
from drf_spectacular.types import OpenApiTypes from drf_spectacular.types import OpenApiTypes
from drf_spectacular.utils import OpenApiParameter, OpenApiResponse, extend_schema from drf_spectacular.utils import OpenApiParameter, OpenApiResponse, extend_schema
@ -20,7 +18,6 @@ from rest_framework.response import Response
from rest_framework.viewsets import ModelViewSet from rest_framework.viewsets import ModelViewSet
from structlog.stdlib import get_logger from structlog.stdlib import get_logger
from authentik.admin.api.metrics import CoordinateSerializer
from authentik.api.pagination import Pagination from authentik.api.pagination import Pagination
from authentik.blueprints.v1.importer import SERIALIZER_CONTEXT_BLUEPRINT from authentik.blueprints.v1.importer import SERIALIZER_CONTEXT_BLUEPRINT
from authentik.core.api.providers import ProviderSerializer from authentik.core.api.providers import ProviderSerializer
@ -28,7 +25,6 @@ from authentik.core.api.used_by import UsedByMixin
from authentik.core.api.utils import ModelSerializer from authentik.core.api.utils import ModelSerializer
from authentik.core.models import Application, User from authentik.core.models import Application, User
from authentik.events.logs import LogEventSerializer, capture_logs from authentik.events.logs import LogEventSerializer, capture_logs
from authentik.events.models import EventAction
from authentik.lib.utils.file import ( from authentik.lib.utils.file import (
FilePathSerializer, FilePathSerializer,
FileUploadSerializer, FileUploadSerializer,
@ -321,18 +317,3 @@ class ApplicationViewSet(UsedByMixin, ModelViewSet):
"""Set application icon (as URL)""" """Set application icon (as URL)"""
app: Application = self.get_object() app: Application = self.get_object()
return set_file_url(request, app, "meta_icon") return set_file_url(request, app, "meta_icon")
@permission_required("authentik_core.view_application", ["authentik_events.view_event"])
@extend_schema(responses={200: CoordinateSerializer(many=True)})
@action(detail=True, pagination_class=None, filter_backends=[])
def metrics(self, request: Request, slug: str):
"""Metrics for application logins"""
app = self.get_object()
return Response(
get_objects_for_user(request.user, "authentik_events.view_event").filter(
action=EventAction.AUTHORIZE_APPLICATION,
context__authorized_application__pk=app.pk.hex,
)
# 3 data points per day, so 8 hour spans
.get_events_per(timedelta(days=7), ExtractHour, 7 * 3)
)

View File

@ -140,6 +140,7 @@ skip = [
"**/storybook-static", "**/storybook-static",
"**/web/src/locales", "**/web/src/locales",
"**/web/xliff", "**/web/xliff",
"**/web/out",
"./web/storybook-static", "./web/storybook-static",
"./web/custom-elements.json", "./web/custom-elements.json",
"./website/build", "./website/build",

View File

@ -1,47 +1,38 @@
import { DEFAULT_CONFIG } from "@goauthentik/common/api/config"; import { DEFAULT_CONFIG } from "@goauthentik/common/api/config";
import { AKChart } from "@goauthentik/elements/charts/Chart"; import { AKChart } from "@goauthentik/elements/charts/Chart";
import { ChartData, Tick } from "chart.js"; import { ChartData } from "chart.js";
import { msg, str } from "@lit/localize"; import { msg } from "@lit/localize";
import { customElement, property } from "lit/decorators.js"; import { customElement, property } from "lit/decorators.js";
import { Coordinate, CoreApi } from "@goauthentik/api"; import { EventActions, EventVolume, EventsApi } from "@goauthentik/api";
@customElement("ak-charts-application-authorize") @customElement("ak-charts-application-authorize")
export class ApplicationAuthorizeChart extends AKChart<Coordinate[]> { export class ApplicationAuthorizeChart extends AKChart<EventVolume[]> {
@property() @property({ attribute: "application-id" })
applicationSlug!: string; applicationId!: string;
async apiRequest(): Promise<Coordinate[]> { async apiRequest(): Promise<EventVolume[]> {
return new CoreApi(DEFAULT_CONFIG).coreApplicationsMetricsList({ return new EventsApi(DEFAULT_CONFIG).eventsEventsVolumeList({
slug: this.applicationSlug, action: EventActions.AuthorizeApplication,
contextAuthorizedApp: this.applicationId.replaceAll("-", ""),
}); });
} }
timeTickCallback(tickValue: string | number, index: number, ticks: Tick[]): string { getChartData(data: EventVolume[]): ChartData {
const valueStamp = ticks[index]; return this.eventVolume(
const delta = Date.now() - valueStamp.value; data,
const ago = Math.round(delta / 1000 / 3600 / 24); new Map([
return msg(str`${ago} days ago`); [
} EventActions.AuthorizeApplication,
getChartData(data: Coordinate[]): ChartData {
return {
datasets: [
{ {
label: msg("Authorizations"), label: msg("Authorizations"),
backgroundColor: "rgba(189, 229, 184, .5)", backgroundColor: "rgba(189, 229, 184, .5)",
spanGaps: true, spanGaps: true,
data:
data.map((cord) => {
return {
x: cord.xCord || 0,
y: cord.yCord || 0,
};
}) || [],
}, },
], ],
}; ]),
);
} }
} }

View File

@ -283,7 +283,7 @@ export class ApplicationViewPage extends AKElement {
<div class="pf-c-card__body"> <div class="pf-c-card__body">
${this.application && ${this.application &&
html` <ak-charts-application-authorize html` <ak-charts-application-authorize
applicationSlug=${this.application.slug} application-id=${this.application.pk}
> >
</ak-charts-application-authorize>`} </ak-charts-application-authorize>`}
</div> </div>