Skip to content

Commit

Permalink
Use AuthnDialog for App sessions.
Browse files Browse the repository at this point in the history
  • Loading branch information
Joerger committed Dec 16, 2024
1 parent af53ac1 commit e3c7edf
Show file tree
Hide file tree
Showing 2 changed files with 41 additions and 30 deletions.
42 changes: 34 additions & 8 deletions web/packages/teleport/src/AppLauncher/AppLauncher.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

import React, { useCallback, useEffect } from 'react';
import { useCallback, useEffect } from 'react';

import { useLocation, useParams } from 'react-router';

Expand All @@ -26,8 +26,11 @@ import { AccessDenied } from 'design/CardError';

import useAttempt from 'shared/hooks/useAttemptNext';

import AuthnDialog from 'teleport/components/AuthnDialog';
import { UrlLauncherParams } from 'teleport/config';
import { useMfa } from 'teleport/lib/useMfa';
import service from 'teleport/services/apps';
import { MfaChallengeScope } from 'teleport/services/auth/auth';

export function AppLauncher() {
const { attempt, setAttempt } = useAttempt('processing');
Expand All @@ -37,6 +40,20 @@ export function AppLauncher() {
const queryParams = new URLSearchParams(search);
const isRedirectFlow = queryParams.get('required-apps');

const mfa = useMfa({
req: {
scope: MfaChallengeScope.USER_SESSION,
allowReuse: false,
isMfaRequiredRequest: {
app: {
fqdn: pathParams.fqdn,
cluster_name: pathParams.clusterId,
public_addr: pathParams.publicAddr,
},
},
},
});

const createAppSession = useCallback(async (params: UrlLauncherParams) => {
let fqdn = params.fqdn;
const port = location.port ? `:${location.port}` : '';
Expand Down Expand Up @@ -101,7 +118,11 @@ export function AppLauncher() {
if (params.arn) {
params.arn = decodeURIComponent(params.arn);
}
const session = await service.createAppSession(params);

// Prompt for MFA if per-session MFA is required for this app.
const mfaResponse = await mfa.getChallengeResponse();

const session = await service.createAppSession(params, mfaResponse);

// Set all the fields expected by server to validate request.
const url = getXTeleportAuthUrl({ fqdn, port });
Expand Down Expand Up @@ -140,13 +161,18 @@ export function AppLauncher() {

useEffect(() => {
createAppSession(pathParams);
}, [pathParams]);

if (attempt.status === 'failed') {
return <AppLauncherAccessDenied statusText={attempt.statusText} />;
}
}, []);

return <AppLauncherProcessing />;
return (
<div>
{attempt.status === 'failed' ? (
<AppLauncherAccessDenied statusText={attempt.statusText} />
) : (
<AppLauncherProcessing />
)}
<AuthnDialog {...mfa}></AuthnDialog>
</div>
);
}

export function AppLauncherProcessing() {
Expand Down
29 changes: 7 additions & 22 deletions web/packages/teleport/src/services/apps/apps.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,11 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

import api from 'teleport/services/api';
import cfg, { UrlAppParams, UrlResourcesParams } from 'teleport/config';
import { ResourcesResponse } from 'teleport/services/agents';
import api from 'teleport/services/api';

import auth, { MfaChallengeScope } from 'teleport/services/auth/auth';
import { MfaChallengeResponse } from '../mfa';

import makeApp from './makeApps';
import { App } from './types';
Expand All @@ -41,27 +41,12 @@ const service = {
});
},

async createAppSession(params: UrlAppParams) {
const resolveApp = {
fqdn: params.fqdn,
cluster_name: params.clusterId,
public_addr: params.publicAddr,
};

// Prompt for MFA if per-session MFA is required for this app.
const challenge = await auth.getMfaChallenge({
scope: MfaChallengeScope.USER_SESSION,
allowReuse: false,
isMfaRequiredRequest: {
app: resolveApp,
},
});

const mfaResponse = await auth.getMfaChallengeResponse(challenge);

async createAppSession(
params: UrlAppParams,
mfaResponse: MfaChallengeResponse
) {
const createAppSession = {
...resolveApp,
arn: params.arn,
...params,
mfaResponse,
// TODO(Joerger): DELETE IN v19.0.0.
// We include a string version of the MFA response for backwards compatibility.
Expand Down

0 comments on commit e3c7edf

Please sign in to comment.