Implement LoginVerifyEmail
This commit is contained in:
parent
438ca4595f
commit
adc6d69201
@ -9,7 +9,7 @@ import fs from "fs";
|
||||
import { join as pathJoin } from "path";
|
||||
import { objectKeys } from "evt/tools/typeSafety/objectKeys";
|
||||
|
||||
export const pageIds= [ "login.ftl", "register.ftl", "info.ftl", "error.ftl", "login-reset-password.ftl"] as const;
|
||||
export const pageIds = ["login.ftl", "register.ftl", "info.ftl", "error.ftl", "login-reset-password.ftl", "login-verify-email.ftl"] as const;
|
||||
|
||||
export type PageId = typeof pageIds[number];
|
||||
|
||||
@ -19,8 +19,14 @@ function loadAdjacentFile(fileBasename: string){
|
||||
};
|
||||
|
||||
function loadFtlFile(ftlFileBasename: PageId | "template.ftl") {
|
||||
try {
|
||||
|
||||
return loadAdjacentFile(ftlFileBasename)
|
||||
.match(/^<script>const _=((?:.|\n)+)<\/script>[\n]?$/)![1];
|
||||
|
||||
} catch {
|
||||
return "{}";
|
||||
}
|
||||
}
|
||||
|
||||
export function generateFtlFilesCodeFactory(
|
||||
|
@ -4,11 +4,11 @@ import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
|
||||
export const Error = memo((props: KcProps) => {
|
||||
|
||||
const { t } = useKcTranslation();
|
||||
const { msg } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
@ -22,7 +22,7 @@ export const Error = memo((props: KcProps) => {
|
||||
<Template
|
||||
{...props}
|
||||
displayMessage={false}
|
||||
headerNode={t("errorTitle")}
|
||||
headerNode={msg("errorTitle")}
|
||||
formNode={
|
||||
<div id="kc-error-message">
|
||||
<p className="instruction">{message.summary}</p>
|
||||
@ -30,7 +30,7 @@ export const Error = memo((props: KcProps) => {
|
||||
client !== undefined && client.baseUrl !== undefined &&
|
||||
<p>
|
||||
<a id="backToApplication" href={client.baseUrl}>
|
||||
{t("backToApplication")}
|
||||
{msg("backToApplication")}
|
||||
</a>
|
||||
</p>
|
||||
}
|
||||
|
@ -4,11 +4,11 @@ import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
|
||||
export const Info = memo((props: KcProps) => {
|
||||
|
||||
const { t } = useKcTranslation();
|
||||
const { msg } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
@ -45,7 +45,7 @@ export const Info = memo((props: KcProps) => {
|
||||
<b>
|
||||
{
|
||||
requiredActions
|
||||
.map(requiredAction => t(`requiredAction.${requiredAction}` as const))
|
||||
.map(requiredAction => msg(`requiredAction.${requiredAction}` as const))
|
||||
.join(",")
|
||||
}
|
||||
|
||||
@ -57,13 +57,13 @@ export const Info = memo((props: KcProps) => {
|
||||
{
|
||||
!skipLink &&
|
||||
pageRedirectUri !== undefined ?
|
||||
<p><a href="${pageRedirectUri}">${(t("backToApplication"))}</a></p>
|
||||
<p><a href="${pageRedirectUri}">${(msg("backToApplication"))}</a></p>
|
||||
:
|
||||
actionUri !== undefined ?
|
||||
<p><a href="${actionUri}">${t("proceedWithAction")}</a></p>
|
||||
<p><a href="${actionUri}">${msg("proceedWithAction")}</a></p>
|
||||
:
|
||||
client.baseUrl !== undefined &&
|
||||
<p><a href="${client.baseUrl}">${t("backToApplication")}</a></p>
|
||||
<p><a href="${client.baseUrl}">${msg("backToApplication")}</a></p>
|
||||
}
|
||||
</div>
|
||||
|
||||
|
@ -8,7 +8,7 @@ import { Register } from "./Register";
|
||||
import { Info } from "./Info";
|
||||
import { Error } from "./Error";
|
||||
import { LoginResetPassword } from "./LoginResetPassword";
|
||||
|
||||
import { LoginVerifyEmail } from "./LoginVerifyEmail";
|
||||
|
||||
export const KcApp = memo((props: KcProps) => {
|
||||
|
||||
@ -20,6 +20,7 @@ export const KcApp = memo((props: KcProps) => {
|
||||
case "info.ftl": return <Info {...props} />;
|
||||
case "error.ftl": return <Error {...props} />;
|
||||
case "login-reset-password.ftl": return <LoginResetPassword {...props} />;
|
||||
case "login-verify-email.ftl": return <LoginVerifyEmail {...props} />;
|
||||
}
|
||||
|
||||
});
|
@ -4,13 +4,13 @@ import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
import { cx } from "tss-react";
|
||||
import { useConstCallback } from "powerhooks";
|
||||
|
||||
export const Login = memo((props: KcProps) => {
|
||||
|
||||
const { t, tStr } = useKcTranslation();
|
||||
const { msg, msgStr } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
@ -34,7 +34,7 @@ export const Login = memo((props: KcProps) => {
|
||||
{...props}
|
||||
displayInfo={social.displayInfo}
|
||||
displayWide={realm.password && social.providers !== undefined}
|
||||
headerNode={t("doLogIn")}
|
||||
headerNode={msg("doLogIn")}
|
||||
formNode={
|
||||
<div
|
||||
id="kc-form"
|
||||
@ -52,12 +52,12 @@ export const Login = memo((props: KcProps) => {
|
||||
<label htmlFor="username" className={cx(props.kcLabelClass)}>
|
||||
{
|
||||
!realm.loginWithEmailAllowed ?
|
||||
t("username")
|
||||
msg("username")
|
||||
:
|
||||
(
|
||||
!realm.registrationEmailAsUsername ?
|
||||
t("usernameOrEmail") :
|
||||
t("email")
|
||||
msg("usernameOrEmail") :
|
||||
msg("email")
|
||||
)
|
||||
}
|
||||
</label>
|
||||
@ -73,7 +73,7 @@ export const Login = memo((props: KcProps) => {
|
||||
</div>
|
||||
<div className={cx(props.kcFormGroupClass)}>
|
||||
<label htmlFor="password" className={cx(props.kcLabelClass)}>
|
||||
{t("password")}
|
||||
{msg("password")}
|
||||
</label>
|
||||
<input tabIndex={2} id="password" className={cx(props.kcInputClass)} name="password" type="password" autoComplete="off" />
|
||||
</div>
|
||||
@ -87,7 +87,7 @@ export const Login = memo((props: KcProps) => {
|
||||
<div className="checkbox">
|
||||
<label>
|
||||
<input tabIndex={3} id="rememberMe" name="rememberMe" type="checkbox" {...(login.rememberMe ? { "checked": true } : {})} />
|
||||
{t("rememberMe")}
|
||||
{msg("rememberMe")}
|
||||
</label>
|
||||
</div>
|
||||
}
|
||||
@ -96,7 +96,7 @@ export const Login = memo((props: KcProps) => {
|
||||
{
|
||||
realm.resetPasswordAllowed &&
|
||||
<span>
|
||||
<a tabIndex={5} href={url.loginResetCredentialsUrl}>{t("doForgotPassword")}</a>
|
||||
<a tabIndex={5} href={url.loginResetCredentialsUrl}>{msg("doForgotPassword")}</a>
|
||||
</span>
|
||||
}
|
||||
</div>
|
||||
@ -112,7 +112,7 @@ export const Login = memo((props: KcProps) => {
|
||||
<input
|
||||
tabIndex={4}
|
||||
className={cx(props.kcButtonClass, props.kcButtonPrimaryClass, props.kcButtonBlockClass, props.kcButtonLargeClass)} name="login" id="kc-login" type="submit"
|
||||
value={tStr("doLogIn")}
|
||||
value={msgStr("doLogIn")}
|
||||
disabled={isLoginButtonDisabled}
|
||||
/>
|
||||
</div>
|
||||
@ -138,7 +138,7 @@ export const Login = memo((props: KcProps) => {
|
||||
}
|
||||
</div>
|
||||
}
|
||||
displayInfoNode={
|
||||
infoNode={
|
||||
(
|
||||
realm.password &&
|
||||
realm.registrationAllowed &&
|
||||
@ -146,9 +146,9 @@ export const Login = memo((props: KcProps) => {
|
||||
) &&
|
||||
<div id="kc-registration">
|
||||
<span>
|
||||
{t("noAccount")}
|
||||
{msg("noAccount")}
|
||||
<a tabIndex={6} href={url.registrationUrl}>
|
||||
{t("doRegister")}
|
||||
{msg("doRegister")}
|
||||
</a>
|
||||
</span>
|
||||
</div>
|
||||
|
@ -4,12 +4,12 @@ import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
import { cx } from "tss-react";
|
||||
|
||||
export const LoginResetPassword = memo((props: KcProps) => {
|
||||
|
||||
const { t, tStr } = useKcTranslation();
|
||||
const { msg, msgStr } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
@ -26,7 +26,7 @@ export const LoginResetPassword = memo((props: KcProps) => {
|
||||
<Template
|
||||
{...props}
|
||||
displayMessage={false}
|
||||
headerNode={t("emailForgotTitle")}
|
||||
headerNode={msg("emailForgotTitle")}
|
||||
formNode={
|
||||
<form id="kc-reset-password-form" className={cx(props.kcFormClass)} action={url.loginAction} method="post">
|
||||
<div className={cx(props.kcFormGroupClass)}>
|
||||
@ -34,11 +34,11 @@ export const LoginResetPassword = memo((props: KcProps) => {
|
||||
<label htmlFor="username" className={cx(props.kcLabelClass)}>
|
||||
{
|
||||
!realm.loginWithEmailAllowed ?
|
||||
t("username")
|
||||
msg("username")
|
||||
:
|
||||
!realm.registrationEmailAsUsername ?
|
||||
t("usernameOrEmail") :
|
||||
t("email")
|
||||
msg("usernameOrEmail") :
|
||||
msg("email")
|
||||
}
|
||||
</label>
|
||||
</div>
|
||||
@ -60,7 +60,7 @@ export const LoginResetPassword = memo((props: KcProps) => {
|
||||
<div id="kc-form-options" className={cx(props.kcFormOptionsClass)}>
|
||||
<div className={cx(props.kcFormOptionsWrapperClass)}>
|
||||
<span>
|
||||
<a href={url.loginUrl}>{t("backToLogin")}</a>
|
||||
<a href={url.loginUrl}>{msg("backToLogin")}</a>
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
@ -72,13 +72,13 @@ export const LoginResetPassword = memo((props: KcProps) => {
|
||||
props.kcButtonBlockClass, props.kcButtonLargeClass
|
||||
)}
|
||||
type="submit"
|
||||
defaultValue={tStr("doSubmit")}
|
||||
defaultValue={msgStr("doSubmit")}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
}
|
||||
infoNode={t("emailInstruction")}
|
||||
infoNode={msg("emailInstruction")}
|
||||
/>
|
||||
);
|
||||
});
|
||||
|
44
src/lib/components/LoginVerifyEmail.tsx
Normal file
44
src/lib/components/LoginVerifyEmail.tsx
Normal file
@ -0,0 +1,44 @@
|
||||
|
||||
import { memo } from "react";
|
||||
import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
|
||||
export const LoginVerifyEmail = memo((props: KcProps) => {
|
||||
|
||||
const { msg } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
kcContext.pageId === "login-verify-email.ftl"
|
||||
);
|
||||
|
||||
const {
|
||||
url
|
||||
} = kcContext;
|
||||
|
||||
return (
|
||||
<Template
|
||||
{...props}
|
||||
displayMessage={false}
|
||||
headerNode={msg("emailVerifyTitle")}
|
||||
formNode={
|
||||
<>
|
||||
<p className="instruction">
|
||||
{msg("emailVerifyInstruction1")}
|
||||
</p>
|
||||
<p className="instruction">
|
||||
{msg("emailVerifyInstruction2")}
|
||||
<a href={url.loginAction}>{msg("doClickHere")}</a>
|
||||
{msg("emailVerifyInstruction3")}
|
||||
</p>
|
||||
</>
|
||||
}
|
||||
/>
|
||||
);
|
||||
|
||||
});
|
||||
|
||||
|
@ -3,12 +3,12 @@ import { Template } from "./Template";
|
||||
import type { KcProps } from "./KcProps";
|
||||
import { assert } from "../tools/assert";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
import { cx } from "tss-react";
|
||||
|
||||
export const Register = memo((props: KcProps) => {
|
||||
|
||||
const { t, tStr } = useKcTranslation();
|
||||
const { msg, msgStr } = useKcMessage();
|
||||
|
||||
assert(
|
||||
kcContext !== undefined &&
|
||||
@ -28,13 +28,13 @@ export const Register = memo((props: KcProps) => {
|
||||
return (
|
||||
<Template
|
||||
{...props}
|
||||
headerNode={t("registerTitle")}
|
||||
headerNode={msg("registerTitle")}
|
||||
formNode={
|
||||
<form id="kc-register-form" className={cx(props.kcFormClass)} action={url.registrationAction} method="post">
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists('firstName', props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="firstName" className={cx(props.kcLabelClass)}>{t("firstName")}</label>
|
||||
<label htmlFor="firstName" className={cx(props.kcLabelClass)}>{msg("firstName")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="text" id="firstName" className={cx(props.kcInputClass)} name="firstName"
|
||||
@ -45,7 +45,7 @@ export const Register = memo((props: KcProps) => {
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists("lastName", props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="lastName" className={cx(props.kcLabelClass)}>{t("lastName")}</label>
|
||||
<label htmlFor="lastName" className={cx(props.kcLabelClass)}>{msg("lastName")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="text" id="lastName" className={cx(props.kcInputClass)} name="lastName"
|
||||
@ -56,7 +56,7 @@ export const Register = memo((props: KcProps) => {
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists('email', props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="email" className={cx(props.kcLabelClass)}>{t("email")}</label>
|
||||
<label htmlFor="email" className={cx(props.kcLabelClass)}>{msg("email")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="text" id="email" className={cx(props.kcInputClass)} name="email"
|
||||
@ -69,7 +69,7 @@ export const Register = memo((props: KcProps) => {
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists('username', props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="username" className={cx(props.kcLabelClass)}>{t("username")}</label>
|
||||
<label htmlFor="username" className={cx(props.kcLabelClass)}>{msg("username")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="text" id="username" className={cx(props.kcInputClass)} name="username"
|
||||
@ -84,7 +84,7 @@ export const Register = memo((props: KcProps) => {
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists("password", props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="password" className={cx(props.kcLabelClass)}>{t("password")}</label>
|
||||
<label htmlFor="password" className={cx(props.kcLabelClass)}>{msg("password")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="password" id="password" className={cx(props.kcInputClass)} name="password" autoComplete="new-password" />
|
||||
@ -93,7 +93,7 @@ export const Register = memo((props: KcProps) => {
|
||||
|
||||
<div className={cx(props.kcFormGroupClass, messagesPerField.printIfExists("password-confirm", props.kcFormGroupErrorClass))}>
|
||||
<div className={cx(props.kcLabelWrapperClass)}>
|
||||
<label htmlFor="password-confirm" className={cx(props.kcLabelClass)}>{t("passwordConfirm")}</label>
|
||||
<label htmlFor="password-confirm" className={cx(props.kcLabelClass)}>{msg("passwordConfirm")}</label>
|
||||
</div>
|
||||
<div className={cx(props.kcInputWrapperClass)}>
|
||||
<input type="password" id="password-confirm" className={cx(props.kcInputClass)} name="password-confirm" />
|
||||
@ -113,13 +113,13 @@ export const Register = memo((props: KcProps) => {
|
||||
<div className={cx(props.kcFormGroupClass)}>
|
||||
<div id="kc-form-options" className={cx(props.kcFormOptionsClass)}>
|
||||
<div className={cx(props.kcFormOptionsWrapperClass)}>
|
||||
<span><a href={url.loginUrl}>{t("backToLogin")}</a></span>
|
||||
<span><a href={url.loginUrl}>{msg("backToLogin")}</a></span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="kc-form-buttons" className={cx(props.kcFormButtonsClass)}>
|
||||
<input className={cx(props.kcButtonClass, props.kcButtonPrimaryClass, props.kcButtonBlockClass, props.kcButtonLargeClass)} type="submit"
|
||||
defaultValue={tStr("doRegister")} />
|
||||
defaultValue={msgStr("doRegister")} />
|
||||
</div>
|
||||
</div>
|
||||
</form >
|
||||
|
@ -1,7 +1,7 @@
|
||||
|
||||
import { useReducer, useEffect, memo } from "react";
|
||||
import type { ReactNode } from "react";
|
||||
import { useKcTranslation } from "../i18n/useKcTranslation";
|
||||
import { useKcMessage } from "../i18n/useKcMessage";
|
||||
import { useKcLanguageTag } from "../i18n/useKcLanguageTag";
|
||||
import { kcContext } from "../kcContext";
|
||||
import { assert } from "../tools/assert";
|
||||
@ -44,7 +44,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
|
||||
useEffect(() => { console.log("Rendering this page with react using keycloakify") }, []);
|
||||
|
||||
const { t } = useKcTranslation();
|
||||
const { msg } = useKcMessage();
|
||||
|
||||
const { kcLanguageTag, setKcLanguageTag } = useKcLanguageTag();
|
||||
|
||||
@ -132,7 +132,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
|
||||
<div id="kc-header" className={cx(props.kcHeaderClass)}>
|
||||
<div id="kc-header-wrapper" className={cx(props.kcHeaderWrapperClass)}>
|
||||
{t("loginTitleHtml", realm.displayNameHtml)}
|
||||
{msg("loginTitleHtml", realm.displayNameHtml)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@ -182,7 +182,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
<div className={cx(props.kcLabelWrapperClass, "subtitle")}>
|
||||
<span className="subtitle">
|
||||
<span className="required">*</span>
|
||||
{t("requiredFields")}
|
||||
{msg("requiredFields")}
|
||||
</span>
|
||||
</div>
|
||||
<div className="col-md-10">
|
||||
@ -201,7 +201,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
displayRequiredFields ? (
|
||||
<div className={cx(props.kcContentWrapperClass)}>
|
||||
<div className={cx(props.kcLabelWrapperClass, "subtitle")}>
|
||||
<span className="subtitle"><span className="required">*</span> {t("requiredFields")}</span>
|
||||
<span className="subtitle"><span className="required">*</span> {msg("requiredFields")}</span>
|
||||
</div>
|
||||
<div className="col-md-10">
|
||||
{showUsernameNode}
|
||||
@ -211,7 +211,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
<a id="reset-login" href={url.loginRestartFlowUrl}>
|
||||
<div className="kc-login-tooltip">
|
||||
<i className={cx(props.kcResetFlowIcon)}></i>
|
||||
<span className="kc-tooltip-text">{t("restartLoginTooltip")}</span>
|
||||
<span className="kc-tooltip-text">{msg("restartLoginTooltip")}</span>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
@ -227,7 +227,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
<a id="reset-login" href={url.loginRestartFlowUrl}>
|
||||
<div className="kc-login-tooltip">
|
||||
<i className={cx(props.kcResetFlowIcon)}></i>
|
||||
<span className="kc-tooltip-text">{t("restartLoginTooltip")}</span>
|
||||
<span className="kc-tooltip-text">{msg("restartLoginTooltip")}</span>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
@ -269,7 +269,7 @@ export const Template = memo((props: TemplateProps) => {
|
||||
<div className={cx(displayWide && [props.kcFormSocialAccountContentClass, props.kcFormSocialAccountClass])} >
|
||||
<div className={cx(props.kcFormGroupClass)}>
|
||||
<input type="hidden" name="tryAnotherWay" value="on" />
|
||||
<a href="#" id="try-another-way" onClick={onTryAnotherWayClick}>{t("doTryAnotherWay")}</a>
|
||||
<a href="#" id="try-another-way" onClick={onTryAnotherWayClick}>{msg("doTryAnotherWay")}</a>
|
||||
</div>
|
||||
</div >
|
||||
</form>
|
||||
|
@ -7,11 +7,11 @@ import { id } from "evt/tools/typeSafety/id";
|
||||
|
||||
export type MessageKey = keyof typeof messages["en"];
|
||||
|
||||
export function useKcTranslation() {
|
||||
export function useKcMessage() {
|
||||
|
||||
const { kcLanguageTag } = useKcLanguageTag();
|
||||
|
||||
const tStr = useConstCallback(
|
||||
const msgStr = useConstCallback(
|
||||
(key: MessageKey, ...args: (string | undefined)[]): string => {
|
||||
|
||||
let str: string = messages[kcLanguageTag as any as "en"][key] ?? messages["en"][key];
|
||||
@ -31,13 +31,13 @@ export function useKcTranslation() {
|
||||
}
|
||||
);
|
||||
|
||||
const t = useConstCallback(
|
||||
id<(...args: Parameters<typeof tStr>) => ReactNode>(
|
||||
const msg = useConstCallback(
|
||||
id<(...args: Parameters<typeof msgStr>) => ReactNode>(
|
||||
(key, ...args) =>
|
||||
<span className={key} dangerouslySetInnerHTML={{ "__html": tStr(key, ...args) }} />
|
||||
<span className={key} dangerouslySetInnerHTML={{ "__html": msgStr(key, ...args) }} />
|
||||
)
|
||||
);
|
||||
|
||||
return { t, tStr };
|
||||
return { msg, msgStr };
|
||||
|
||||
}
|
@ -2,7 +2,7 @@ export * from "./kcContext";
|
||||
|
||||
export * from "./i18n/KcLanguageTag";
|
||||
export * from "./i18n/useKcLanguageTag";
|
||||
export * from "./i18n/useKcTranslation";
|
||||
export * from "./i18n/useKcMessage";
|
||||
|
||||
export * from "./components/KcProps";
|
||||
export * from "./components/Login";
|
||||
@ -10,5 +10,7 @@ export * from "./components/Template";
|
||||
export * from "./components/KcApp";
|
||||
export * from "./components/Info";
|
||||
export * from "./components/Error";
|
||||
export * from "./components/LoginResetPassword";
|
||||
export * from "./components/LoginVerifyEmail";
|
||||
|
||||
export * from "./tools/assert";
|
@ -4,13 +4,15 @@ import type { PageId } from "../bin/build-keycloak-theme/generateFtl";
|
||||
import { id } from "evt/tools/typeSafety/id";
|
||||
import type { KcLanguageTag } from "./i18n/KcLanguageTag";
|
||||
import { doExtends } from "evt/tools/typeSafety/doExtends";
|
||||
import type { MessageKey } from "./i18n/useKcTranslation";
|
||||
import type { LanguageLabel } from "./i18n/KcLanguageTag";
|
||||
import type { MessageKey } from "./i18n/useKcMessage";
|
||||
import type { LanguageLabel } from "./i18n/KcLanguageTag";
|
||||
|
||||
type ExtractAfterStartingWith<Prefix extends string, StrEnum> =
|
||||
StrEnum extends `${Prefix}${infer U}` ? U : never;
|
||||
|
||||
export type KcContext = KcContext.Login | KcContext.Register | KcContext.Info | KcContext.Error | KcContext.LoginResetPassword;
|
||||
export type KcContext =
|
||||
KcContext.Login | KcContext.Register | KcContext.Info |
|
||||
KcContext.Error | KcContext.LoginResetPassword | KcContext.LoginVerifyEmail;
|
||||
export declare namespace KcContext {
|
||||
|
||||
export type Template = {
|
||||
@ -122,7 +124,7 @@ export declare namespace KcContext {
|
||||
export type Info = Template & {
|
||||
pageId: "info.ftl";
|
||||
messageHeader?: string;
|
||||
requiredActions?: ExtractAfterStartingWith<"requiredAction.",MessageKey>[];
|
||||
requiredActions?: ExtractAfterStartingWith<"requiredAction.", MessageKey>[];
|
||||
skipLink: boolean;
|
||||
pageRedirectUri?: string;
|
||||
actionUri?: string;
|
||||
@ -145,6 +147,10 @@ export declare namespace KcContext {
|
||||
}
|
||||
};
|
||||
|
||||
export type LoginVerifyEmail = Template & {
|
||||
pageId: "login-verify-email.ftl";
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
doExtends<KcContext["pageId"], PageId>();
|
||||
|
Loading…
x
Reference in New Issue
Block a user