session item rehaul, finish session util

This commit is contained in:
Max Peintner
2024-10-30 13:59:03 +01:00
parent cd6a11e269
commit 050ef343fe
5 changed files with 102 additions and 89 deletions

View File

@@ -34,33 +34,10 @@ export function IdpSignin({
idpIntentToken,
},
authRequestId,
})
.then((session) => {
if (authRequestId && session && session.id) {
return router.push(
`/login?` +
new URLSearchParams({
sessionId: session.id,
authRequest: authRequestId,
}),
);
} else {
const params = new URLSearchParams({});
if (session.factors?.user?.loginName) {
params.set("loginName", session.factors?.user?.loginName);
}
if (authRequestId) {
params.set("authRequestId", authRequestId);
}
return router.push(`/signedin?` + params);
}
})
.catch((error) => {
setError(error.message);
return;
});
}).catch((error) => {
setError(error.message);
return;
});
setLoading(false);
}, []);

View File

@@ -1,11 +1,11 @@
"use client";
import { cleanupSession } from "@/lib/server/session";
import { sendLoginname } from "@/lib/server/loginname";
import { cleanupSession, continueWithSession } from "@/lib/server/session";
import { XCircleIcon } from "@heroicons/react/24/outline";
import { Timestamp, timestampDate } from "@zitadel/client";
import { Session } from "@zitadel/proto/zitadel/session/v2/session_pb";
import moment from "moment";
import Link from "next/link";
import { useState } from "react";
import { Avatar } from "./avatar";
@@ -53,42 +53,21 @@ export function SessionItem({
const [error, setError] = useState<string | null>(null);
return (
<Link
prefetch={false}
href={
valid && authRequestId
? `/login?` +
new URLSearchParams({
// loginName: session.factors?.user?.loginName as string,
sessionId: session.id,
authRequest: authRequestId,
})
: !valid
? `/loginname?` +
new URLSearchParams(
authRequestId
? {
loginName: session.factors?.user?.loginName as string,
submit: "true",
authRequestId,
}
: {
loginName: session.factors?.user?.loginName as string,
submit: "true",
},
)
: "/signedin?" +
new URLSearchParams(
authRequestId
? {
loginName: session.factors?.user?.loginName as string,
authRequestId,
}
: {
loginName: session.factors?.user?.loginName as string,
},
)
}
<button
onClick={() => {
if (valid && session?.factors?.user) {
return continueWithSession({
...session,
authRequestId: authRequestId,
});
} else if (session.factors?.user) {
return sendLoginname({
loginName: session.factors?.user?.loginName,
organization: session.factors.user.organizationId,
authRequestId: authRequestId,
});
}
}}
className="group flex flex-row items-center bg-background-light-400 dark:bg-background-dark-400 border border-divider-light hover:shadow-lg dark:hover:bg-white/10 py-2 px-4 rounded-md transition-all"
>
<div className="pr-4">
@@ -129,6 +108,6 @@ export function SessionItem({
}}
/>
</div>
</Link>
</button>
);
}

View File

@@ -0,0 +1,32 @@
import { redirect } from "next/navigation";
type FinishFlowCommand =
| {
sessionId: string;
authRequestId: string;
}
| { loginName: string };
/**
* redirects user back to OIDC application or to a success page
* @param command
* @returns
*/
export function finishFlow(
command: FinishFlowCommand & { organization?: string },
) {
return "sessionId" in command && "authRequestId" in command
? redirect(
`/login?` +
new URLSearchParams({
sessionId: command.sessionId,
authRequest: command.authRequestId,
}),
)
: redirect(
`/signedin?` +
new URLSearchParams({
loginName: command.loginName,
}),
);
}

View File

@@ -21,6 +21,7 @@ import { AuthenticationMethodType } from "@zitadel/proto/zitadel/user/v2/user_se
import { headers } from "next/headers";
import { redirect } from "next/navigation";
import { getSessionCookieByLoginName } from "../cookies";
import { finishFlow } from "../login";
type ResetPasswordCommand = {
loginName: string;
@@ -239,36 +240,19 @@ export async function sendPassword(command: UpdateSessionCommand) {
// return router.push(`/passkey/set?` + params);
// }
else if (command.authRequestId && submitted.sessionId) {
const params = new URLSearchParams({
sessionId: submitted.sessionId,
authRequest: command.authRequestId,
});
if (command.organization) {
params.append("organization", command.organization);
}
return redirect(`/login?` + params);
}
// without OIDC flow
const params = new URLSearchParams(
command.authRequestId
return finishFlow(
command.authRequestId && submitted.sessionId
? {
loginName: submitted.factors.user.loginName,
sessionId: submitted.sessionId,
authRequestId: command.authRequestId,
organization: submitted.factors.user.organizationId,
}
: {
loginName: submitted.factors.user.loginName,
organization: submitted.factors.user.organizationId,
},
);
if (command.organization) {
params.append("organization", command.organization);
}
return redirect(`/signedin?` + params);
}
export async function changePassword(command: {

View File

@@ -6,6 +6,7 @@ import {
} from "@/lib/server/cookie";
import { deleteSession, listAuthenticationMethodTypes } from "@/lib/zitadel";
import { RequestChallenges } from "@zitadel/proto/zitadel/session/v2/challenge_pb";
import { Session } from "@zitadel/proto/zitadel/session/v2/session_pb";
import { Checks } from "@zitadel/proto/zitadel/session/v2/session_service_pb";
import { headers } from "next/headers";
import {
@@ -14,6 +15,7 @@ import {
getSessionCookieByLoginName,
removeSessionFromCookie,
} from "../cookies";
import { finishFlow } from "../login";
type CreateNewSessionCommand = {
userId: string;
@@ -32,7 +34,46 @@ export async function createNewSessionForIdp(options: CreateNewSessionCommand) {
if (!userId || !idpIntent) {
throw new Error("No userId or loginName provided");
}
return createSessionForIdpAndUpdateCookie(userId, idpIntent, authRequestId);
const session = await createSessionForIdpAndUpdateCookie(
userId,
idpIntent,
authRequestId,
);
if (!session || !session.factors?.user) {
return { error: "Could not create session" };
}
return finishFlow(
authRequestId && session.id
? {
sessionId: session.id,
authRequestId: authRequestId,
organization: session.factors.user.organizationId,
}
: {
loginName: session.factors.user.loginName,
organization: session.factors.user.organizationId,
},
);
}
export async function continueWithSession({
authRequestId,
...session
}: Session & { authRequestId?: string }) {
return authRequestId && session.id && session.factors?.user
? finishFlow({
sessionId: session.id,
authRequestId: authRequestId,
organization: session.factors.user.organizationId,
})
: session.factors?.user
? finishFlow({
loginName: session.factors.user.loginName,
organization: session.factors.user.organizationId,
})
: null;
}
export type UpdateSessionCommand = {