core: fix app launch URL flow selection (#5113)
This commit is contained in:
parent
73bf6fd530
commit
75510ead84
|
@ -12,16 +12,19 @@ from authentik.flows.challenge import (
|
||||||
RedirectChallenge,
|
RedirectChallenge,
|
||||||
)
|
)
|
||||||
from authentik.flows.exceptions import FlowNonApplicableException
|
from authentik.flows.exceptions import FlowNonApplicableException
|
||||||
from authentik.flows.models import in_memory_stage
|
from authentik.flows.models import FlowDesignation, in_memory_stage
|
||||||
from authentik.flows.planner import PLAN_CONTEXT_APPLICATION, FlowPlanner
|
from authentik.flows.planner import PLAN_CONTEXT_APPLICATION, FlowPlanner
|
||||||
from authentik.flows.stage import ChallengeStageView
|
from authentik.flows.stage import ChallengeStageView
|
||||||
from authentik.flows.views.executor import SESSION_KEY_PLAN
|
from authentik.flows.views.executor import (
|
||||||
|
SESSION_KEY_APPLICATION_PRE,
|
||||||
|
SESSION_KEY_PLAN,
|
||||||
|
ToDefaultFlow,
|
||||||
|
)
|
||||||
from authentik.lib.utils.urls import redirect_with_qs
|
from authentik.lib.utils.urls import redirect_with_qs
|
||||||
from authentik.stages.consent.stage import (
|
from authentik.stages.consent.stage import (
|
||||||
PLAN_CONTEXT_CONSENT_HEADER,
|
PLAN_CONTEXT_CONSENT_HEADER,
|
||||||
PLAN_CONTEXT_CONSENT_PERMISSIONS,
|
PLAN_CONTEXT_CONSENT_PERMISSIONS,
|
||||||
)
|
)
|
||||||
from authentik.tenants.models import Tenant
|
|
||||||
|
|
||||||
|
|
||||||
class RedirectToAppLaunch(View):
|
class RedirectToAppLaunch(View):
|
||||||
|
@ -36,10 +39,10 @@ class RedirectToAppLaunch(View):
|
||||||
# Check if we're authenticated already, saves us the flow run
|
# Check if we're authenticated already, saves us the flow run
|
||||||
if request.user.is_authenticated:
|
if request.user.is_authenticated:
|
||||||
return HttpResponseRedirect(app.get_launch_url(request.user))
|
return HttpResponseRedirect(app.get_launch_url(request.user))
|
||||||
|
self.request.session[SESSION_KEY_APPLICATION_PRE] = app
|
||||||
# otherwise, do a custom flow plan that includes the application that's
|
# otherwise, do a custom flow plan that includes the application that's
|
||||||
# being accessed, to improve usability
|
# being accessed, to improve usability
|
||||||
tenant: Tenant = request.tenant
|
flow = ToDefaultFlow(request=request, designation=FlowDesignation.AUTHENTICATION).get_flow()
|
||||||
flow = tenant.flow_authentication
|
|
||||||
planner = FlowPlanner(flow)
|
planner = FlowPlanner(flow)
|
||||||
planner.allow_empty_flows = True
|
planner.allow_empty_flows = True
|
||||||
try:
|
try:
|
||||||
|
|
|
@ -476,26 +476,32 @@ class ToDefaultFlow(View):
|
||||||
LOGGER.debug("flow_by_policy: no flow found", filters=flow_filter)
|
LOGGER.debug("flow_by_policy: no flow found", filters=flow_filter)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
def dispatch(self, request: HttpRequest) -> HttpResponse:
|
def get_flow(self) -> Flow:
|
||||||
tenant: Tenant = request.tenant
|
"""Get a flow for the selected designation"""
|
||||||
|
tenant: Tenant = self.request.tenant
|
||||||
flow = None
|
flow = None
|
||||||
# First, attempt to get default flow from tenant
|
# First, attempt to get default flow from tenant
|
||||||
if self.designation == FlowDesignation.AUTHENTICATION:
|
if self.designation == FlowDesignation.AUTHENTICATION:
|
||||||
# Attempt to get default flow from application
|
|
||||||
if SESSION_KEY_APPLICATION_PRE in self.request.session:
|
|
||||||
application: Application = self.request.session[SESSION_KEY_APPLICATION_PRE]
|
|
||||||
if application.provider:
|
|
||||||
flow = application.provider.authentication_flow
|
|
||||||
else:
|
|
||||||
flow = tenant.flow_authentication
|
flow = tenant.flow_authentication
|
||||||
|
# Check if we have a default flow from application
|
||||||
|
application: Optional[Application] = self.request.session.get(
|
||||||
|
SESSION_KEY_APPLICATION_PRE
|
||||||
|
)
|
||||||
|
if application and application.provider and application.provider.authentication_flow:
|
||||||
|
flow = application.provider.authentication_flow
|
||||||
elif self.designation == FlowDesignation.INVALIDATION:
|
elif self.designation == FlowDesignation.INVALIDATION:
|
||||||
flow = tenant.flow_invalidation
|
flow = tenant.flow_invalidation
|
||||||
|
if flow:
|
||||||
|
return flow
|
||||||
# If no flow was set, get the first based on slug and policy
|
# If no flow was set, get the first based on slug and policy
|
||||||
if not flow:
|
flow = self.flow_by_policy(self.request, designation=self.designation)
|
||||||
flow = self.flow_by_policy(request, designation=self.designation)
|
if flow:
|
||||||
|
return flow
|
||||||
# If we still don't have a flow, 404
|
# If we still don't have a flow, 404
|
||||||
if not flow:
|
|
||||||
raise Http404
|
raise Http404
|
||||||
|
|
||||||
|
def dispatch(self, request: HttpRequest) -> HttpResponse:
|
||||||
|
flow = self.get_flow()
|
||||||
# If user already has a pending plan, clear it so we don't have to later.
|
# If user already has a pending plan, clear it so we don't have to later.
|
||||||
if SESSION_KEY_PLAN in self.request.session:
|
if SESSION_KEY_PLAN in self.request.session:
|
||||||
plan: FlowPlan = self.request.session[SESSION_KEY_PLAN]
|
plan: FlowPlan = self.request.session[SESSION_KEY_PLAN]
|
||||||
|
|
Reference in New Issue