Skip to content

[FEATURE] RADIUS Outpost proxy with Out-of-Band (OOB) Web Flow for VPN & SSH MFA #886

@mTrax-

Description

@mTrax-

Is your feature request related to a problem? Please describe.

No response

Describe the solution you'd like.

Context

Enterprise network hardware (like UniFi UDM routers) and server infrastructure (SSH via PAM) rely on legacy authentication protocols (RADIUS/PAP). To enforce per-session MFA for cyber-insurance compliance, a proxy is required to bridge these legacy systems with modern identity providers.

The Challenge: Headless Protocols vs Upstream MFA

Legacy clients (VPN, SSH) are headless and only transmit raw text credentials. They cannot render web-based OIDC/SAML login pages or handle upstream MFA prompts (such as Google Workspace or Microsoft Entra ID 2FA).

Using backend validation workarounds (like LDAP or App Passwords) either requires costly licensing or introduces persistent credentials that bypass MFA, violating modern security policies.

The Solution: Out-of-Band (OOB) Web Authentication

The cleanest, most secure approach (similar to systems like Authentik) is to decouple the authentication by shifting it to the user's mobile browser. This allows the reuse of Tinyauth's existing OIDC federation capabilities without implementing local MFA storage or custom mobile apps.

Proposed Architecture:

  1. A standalone, lightweight Go daemon (tinyauth-radius-outpost) utilizing layeh/radius or its updated fork inverse-inc/go-radius listens for incoming Access-Request packets.
  2. The Outpost proxies the request to Tinyauth via an internal API.
  3. Tinyauth holds the API response and triggers an out-of-band workflow via webhooks.

Step 1: Initialization

The user connects to the VPN or SSH server using their username and a placeholder/dummy password (e.g., vpn).
The Outpost captures this and sends an HTTP POST to Tinyauth:
POST /api/internal/radius/initiate
Payload:

{
  "username": "user@domain.com",
  "nas_ip": "192.168.1.1",
  "service": "vpn" 
}

Step 2: Magic Link Generation & Insurance Compliance

Tinyauth holds the HTTP connection open and generates a unique, short-lived login token (Magic Link).

Ensuring Systematic MFA (Cyber-Insurance Requirement):
To prevent the user's mobile browser from silently reusing an existing Google/Entra session cookie (which would bypass MFA), Tinyauth must construct the upstream OIDC authorization request with specific parameters:

  • login_hint=user@domain.com (To pre-fill the identity field for a seamless UX)
  • prompt=login (To explicitly force the upstream IdP to challenge the user for password and MFA on every single connection)

Step 3: Out-of-Band Notification

Tinyauth fires a webhook payload to a notification service (like ntfy.sh or a custom dispatch) to push the interactive Magic Link to the user's registered mobile device.

Step 4: Verification & Release

  1. The user taps the notification, opening their mobile browser.
  2. They complete the standard Tinyauth authentication flow, which redirects them to the upstream provider where MFA is enforced due to prompt=login.
  3. Upon successful OIDC callback, Tinyauth marks the pending RADIUS session as authorized.
  4. Tinyauth releases the held request from Step 1, returning 200 OK to the Outpost.
  5. The Outpost sends an Access-Accept packet back to the network hardware or PAM module.

Broader Use Cases

Implementing this API-first OOB pattern allows Tinyauth to secure multiple infrastructure entry points beyond enterprise VPNs, including:

  • SSH Access: Securing server access by pairing the RADIUS Outpost with pam_radius_auth on Linux systems.
  • Network Infrastructure: Enforcing MFA for administrative access to switches, firewalls, and routers.

This design keeps Tinyauth strictly focused on web-based IAM logic while providing an elegant, scalable integration pathway for legacy infrastructure.

Describe alternatives you've considered.

No response

Additional context

No response

Human Written Confirmation

  • I confirm this request was written by me and not generated by an LLM or AI assistant.

Metadata

Metadata

Assignees

Labels

enhancementNew feature or request

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions