keycloakify 10.0.0-rc.36 → 10.0.0-rc.38
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/account/Fallback.d.ts +1 -2
- package/account/Fallback.js.map +1 -1
- package/account/KcContext/KcContext.d.ts +6 -6
- package/account/KcContext/getKcContextMock.d.ts +9 -9
- package/account/KcContext/getKcContextMock.js +3 -3
- package/account/KcContext/getKcContextMock.js.map +1 -1
- package/account/Template.d.ts +1 -2
- package/account/Template.js +7 -6
- package/account/Template.js.map +1 -1
- package/account/TemplateProps.d.ts +1 -3
- package/account/i18n/i18n.d.ts +9 -4
- package/account/i18n/i18n.js +132 -87
- package/account/i18n/i18n.js.map +1 -1
- package/account/i18n/index.d.ts +9 -2
- package/account/i18n/index.js +5 -1
- package/account/i18n/index.js.map +1 -1
- package/account/index.d.ts +1 -1
- package/account/lib/kcClsx.d.ts +9 -0
- package/account/lib/{useGetClassName.js → kcClsx.js} +3 -3
- package/account/lib/kcClsx.js.map +1 -0
- package/account/pages/Account.d.ts +1 -2
- package/account/pages/Account.js +9 -7
- package/account/pages/Account.js.map +1 -1
- package/account/pages/Applications.d.ts +1 -2
- package/account/pages/Applications.js +7 -7
- package/account/pages/Applications.js.map +1 -1
- package/account/pages/FederatedIdentity.d.ts +1 -2
- package/account/pages/FederatedIdentity.js +4 -3
- package/account/pages/FederatedIdentity.js.map +1 -1
- package/account/pages/Log.d.ts +1 -2
- package/account/pages/Log.js +6 -5
- package/account/pages/Log.js.map +1 -1
- package/account/pages/PageProps.d.ts +2 -4
- package/account/pages/Password.d.ts +1 -2
- package/account/pages/Password.js +10 -9
- package/account/pages/Password.js.map +1 -1
- package/account/pages/Sessions.d.ts +1 -2
- package/account/pages/Sessions.js +6 -6
- package/account/pages/Sessions.js.map +1 -1
- package/account/pages/Totp.d.ts +1 -2
- package/account/pages/Totp.js +6 -5
- package/account/pages/Totp.js.map +1 -1
- package/bin/{314.index.js → 21.index.js} +162 -4
- package/bin/{430.index.js → 214.index.js} +161 -2
- package/bin/3.index.js +81 -65
- package/bin/526.index.js +3 -2
- package/bin/538.index.js +552 -0
- package/bin/795.index.js +3 -2
- package/bin/{890.index.js → 941.index.js} +2 -159
- package/bin/main.js +19 -7
- package/lib/getKcClsx.d.ts +11 -0
- package/lib/getKcClsx.js +44 -0
- package/lib/getKcClsx.js.map +1 -0
- package/login/Fallback.d.ts +1 -2
- package/login/Fallback.js.map +1 -1
- package/login/KcContext/KcContext.d.ts +6 -6
- package/login/KcContext/getKcContextMock.d.ts +9 -9
- package/login/KcContext/getKcContextMock.js +3 -3
- package/login/KcContext/getKcContextMock.js.map +1 -1
- package/login/Template.d.ts +1 -2
- package/login/Template.js +10 -9
- package/login/Template.js.map +1 -1
- package/login/TemplateProps.d.ts +1 -3
- package/login/UserProfileFormFields.d.ts +5 -5
- package/login/UserProfileFormFields.js +35 -34
- package/login/UserProfileFormFields.js.map +1 -1
- package/login/i18n/i18n.d.ts +9 -4
- package/login/i18n/i18n.js +136 -91
- package/login/i18n/i18n.js.map +1 -1
- package/login/i18n/index.d.ts +9 -2
- package/login/i18n/index.js +5 -1
- package/login/i18n/index.js.map +1 -1
- package/login/index.d.ts +1 -1
- package/login/lib/kcClsx.d.ts +9 -0
- package/login/lib/{useGetClassName.js → kcClsx.js} +3 -3
- package/login/lib/kcClsx.js.map +1 -0
- package/login/lib/useUserProfileForm.d.ts +9 -6
- package/login/lib/useUserProfileForm.js +7 -5
- package/login/lib/useUserProfileForm.js.map +1 -1
- package/login/pages/Code.d.ts +1 -2
- package/login/pages/Code.js +6 -5
- package/login/pages/Code.js.map +1 -1
- package/login/pages/DeleteAccountConfirm.d.ts +1 -2
- package/login/pages/DeleteAccountConfirm.js +7 -7
- package/login/pages/DeleteAccountConfirm.js.map +1 -1
- package/login/pages/DeleteCredential.d.ts +1 -2
- package/login/pages/DeleteCredential.js +6 -6
- package/login/pages/DeleteCredential.js.map +1 -1
- package/login/pages/Error.d.ts +1 -2
- package/login/pages/Error.js +4 -3
- package/login/pages/Error.js.map +1 -1
- package/login/pages/FrontchannelLogout.d.ts +1 -2
- package/login/pages/FrontchannelLogout.js +4 -3
- package/login/pages/FrontchannelLogout.js.map +1 -1
- package/login/pages/IdpReviewUserProfile.d.ts +1 -2
- package/login/pages/IdpReviewUserProfile.js +6 -6
- package/login/pages/IdpReviewUserProfile.js.map +1 -1
- package/login/pages/Info.d.ts +1 -2
- package/login/pages/Info.js +4 -3
- package/login/pages/Info.js.map +1 -1
- package/login/pages/Login.d.ts +1 -2
- package/login/pages/Login.js +10 -8
- package/login/pages/Login.js.map +1 -1
- package/login/pages/LoginConfigTotp.d.ts +1 -2
- package/login/pages/LoginConfigTotp.js +8 -7
- package/login/pages/LoginConfigTotp.js.map +1 -1
- package/login/pages/LoginIdpLinkConfirm.d.ts +1 -2
- package/login/pages/LoginIdpLinkConfirm.js +6 -6
- package/login/pages/LoginIdpLinkConfirm.js.map +1 -1
- package/login/pages/LoginIdpLinkEmail.d.ts +1 -2
- package/login/pages/LoginIdpLinkEmail.js +4 -3
- package/login/pages/LoginIdpLinkEmail.js.map +1 -1
- package/login/pages/LoginOauth2DeviceVerifyUserCode.d.ts +1 -2
- package/login/pages/LoginOauth2DeviceVerifyUserCode.js +6 -6
- package/login/pages/LoginOauth2DeviceVerifyUserCode.js.map +1 -1
- package/login/pages/LoginOauthGrant.d.ts +1 -2
- package/login/pages/LoginOauthGrant.js +7 -7
- package/login/pages/LoginOauthGrant.js.map +1 -1
- package/login/pages/LoginOtp.d.ts +1 -2
- package/login/pages/LoginOtp.js +6 -6
- package/login/pages/LoginOtp.js.map +1 -1
- package/login/pages/LoginPageExpired.d.ts +1 -2
- package/login/pages/LoginPageExpired.js +4 -3
- package/login/pages/LoginPageExpired.js.map +1 -1
- package/login/pages/LoginPassword.d.ts +1 -2
- package/login/pages/LoginPassword.js +9 -7
- package/login/pages/LoginPassword.js.map +1 -1
- package/login/pages/LoginRecoveryAuthnCodeConfig.d.ts +1 -2
- package/login/pages/LoginRecoveryAuthnCodeConfig.js +9 -7
- package/login/pages/LoginRecoveryAuthnCodeConfig.js.map +1 -1
- package/login/pages/LoginRecoveryAuthnCodeInput.d.ts +1 -2
- package/login/pages/LoginRecoveryAuthnCodeInput.js +6 -6
- package/login/pages/LoginRecoveryAuthnCodeInput.js.map +1 -1
- package/login/pages/LoginResetOtp.d.ts +1 -2
- package/login/pages/LoginResetOtp.js +6 -6
- package/login/pages/LoginResetOtp.js.map +1 -1
- package/login/pages/LoginResetPassword.d.ts +1 -2
- package/login/pages/LoginResetPassword.js +7 -7
- package/login/pages/LoginResetPassword.js.map +1 -1
- package/login/pages/LoginUpdatePassword.d.ts +1 -2
- package/login/pages/LoginUpdatePassword.js +10 -9
- package/login/pages/LoginUpdatePassword.js.map +1 -1
- package/login/pages/LoginUpdateProfile.d.ts +1 -2
- package/login/pages/LoginUpdateProfile.js +7 -12
- package/login/pages/LoginUpdateProfile.js.map +1 -1
- package/login/pages/LoginUsername.d.ts +1 -2
- package/login/pages/LoginUsername.js +8 -7
- package/login/pages/LoginUsername.js.map +1 -1
- package/login/pages/LoginVerifyEmail.d.ts +1 -2
- package/login/pages/LoginVerifyEmail.js +4 -3
- package/login/pages/LoginVerifyEmail.js.map +1 -1
- package/login/pages/LoginX509Info.d.ts +1 -2
- package/login/pages/LoginX509Info.js +6 -6
- package/login/pages/LoginX509Info.js.map +1 -1
- package/login/pages/LogoutConfirm.d.ts +1 -2
- package/login/pages/LogoutConfirm.js +6 -6
- package/login/pages/LogoutConfirm.js.map +1 -1
- package/login/pages/PageProps.d.ts +2 -4
- package/login/pages/Register.d.ts +1 -2
- package/login/pages/Register.js +8 -16
- package/login/pages/Register.js.map +1 -1
- package/login/pages/SamlPostForm.d.ts +1 -2
- package/login/pages/SamlPostForm.js +4 -3
- package/login/pages/SamlPostForm.js.map +1 -1
- package/login/pages/SelectAuthenticator.d.ts +1 -2
- package/login/pages/SelectAuthenticator.js +6 -9
- package/login/pages/SelectAuthenticator.js.map +1 -1
- package/login/pages/Terms.d.ts +1 -2
- package/login/pages/Terms.js +7 -7
- package/login/pages/Terms.js.map +1 -1
- package/login/pages/UpdateEmail.d.ts +1 -2
- package/login/pages/UpdateEmail.js +8 -12
- package/login/pages/UpdateEmail.js.map +1 -1
- package/login/pages/WebauthnAuthenticate.d.ts +1 -2
- package/login/pages/WebauthnAuthenticate.js +13 -12
- package/login/pages/WebauthnAuthenticate.js.map +1 -1
- package/login/pages/WebauthnError.d.ts +1 -2
- package/login/pages/WebauthnError.js +7 -7
- package/login/pages/WebauthnError.js.map +1 -1
- package/login/pages/WebauthnRegister.d.ts +1 -2
- package/login/pages/WebauthnRegister.js +9 -8
- package/login/pages/WebauthnRegister.js.map +1 -1
- package/package.json +24 -16
- package/src/account/Fallback.tsx +1 -2
- package/src/account/KcContext/KcContext.ts +7 -7
- package/src/account/KcContext/getKcContextMock.ts +13 -24
- package/src/account/Template.tsx +8 -8
- package/src/account/TemplateProps.ts +1 -6
- package/src/account/i18n/i18n.tsx +204 -125
- package/src/account/i18n/index.ts +10 -2
- package/src/account/index.ts +1 -1
- package/src/account/lib/{useGetClassName.ts → kcClsx.ts} +6 -2
- package/src/account/pages/Account.tsx +15 -21
- package/src/account/pages/Applications.tsx +8 -9
- package/src/account/pages/FederatedIdentity.tsx +5 -5
- package/src/account/pages/Log.tsx +8 -8
- package/src/account/pages/PageProps.ts +2 -4
- package/src/account/pages/Password.tsx +13 -16
- package/src/account/pages/Sessions.tsx +9 -10
- package/src/account/pages/Totp.tsx +19 -28
- package/src/bin/keycloakify/generateSrcMainResources/generateMessageProperties.ts +2 -66
- package/src/bin/keycloakify/generateSrcMainResources/generateSrcMainResourcesForMainTheme.ts +7 -1
- package/src/bin/main.ts +15 -0
- package/src/bin/shared/buildOptions.ts +5 -2
- package/src/bin/shared/generateKcGenTs.ts +61 -0
- package/src/bin/tools/escapeStringForPropertiesFile.ts +64 -0
- package/src/bin/update-kc-gen.ts +13 -0
- package/src/lib/getKcClsx.ts +75 -0
- package/src/login/Fallback.tsx +1 -2
- package/src/login/KcContext/KcContext.ts +7 -7
- package/src/login/KcContext/getKcContextMock.ts +13 -24
- package/src/login/Template.tsx +36 -37
- package/src/login/TemplateProps.ts +1 -6
- package/src/login/UserProfileFormFields.tsx +66 -81
- package/src/login/i18n/i18n.tsx +208 -129
- package/src/login/i18n/index.ts +10 -2
- package/src/login/index.ts +1 -1
- package/src/login/lib/{useGetClassName.ts → kcClsx.ts} +6 -2
- package/src/login/lib/useUserProfileForm.tsx +29 -21
- package/src/login/pages/Code.tsx +10 -8
- package/src/login/pages/DeleteAccountConfirm.tsx +9 -10
- package/src/login/pages/DeleteCredential.tsx +11 -10
- package/src/login/pages/Error.tsx +5 -5
- package/src/login/pages/FrontchannelLogout.tsx +7 -5
- package/src/login/pages/IdpReviewUserProfile.tsx +16 -25
- package/src/login/pages/Info.tsx +7 -5
- package/src/login/pages/Login.tsx +34 -53
- package/src/login/pages/LoginConfigTotp.tsx +30 -38
- package/src/login/pages/LoginIdpLinkConfirm.tsx +10 -21
- package/src/login/pages/LoginIdpLinkEmail.tsx +5 -5
- package/src/login/pages/LoginOauth2DeviceVerifyUserCode.tsx +19 -24
- package/src/login/pages/LoginOauthGrant.tsx +14 -21
- package/src/login/pages/LoginOtp.tsx +29 -33
- package/src/login/pages/LoginPageExpired.tsx +5 -5
- package/src/login/pages/LoginPassword.tsx +23 -33
- package/src/login/pages/LoginRecoveryAuthnCodeConfig.tsx +21 -25
- package/src/login/pages/LoginRecoveryAuthnCodeInput.tsx +21 -25
- package/src/login/pages/LoginResetOtp.tsx +21 -25
- package/src/login/pages/LoginResetPassword.tsx +21 -25
- package/src/login/pages/LoginUpdatePassword.tsx +42 -52
- package/src/login/pages/LoginUpdateProfile.tsx +26 -33
- package/src/login/pages/LoginUsername.tsx +23 -35
- package/src/login/pages/LoginVerifyEmail.tsx +7 -5
- package/src/login/pages/LoginX509Info.tsx +27 -36
- package/src/login/pages/LogoutConfirm.tsx +11 -17
- package/src/login/pages/PageProps.ts +2 -4
- package/src/login/pages/Register.tsx +24 -49
- package/src/login/pages/SamlPostForm.tsx +5 -5
- package/src/login/pages/SelectAuthenticator.tsx +24 -26
- package/src/login/pages/Terms.tsx +11 -18
- package/src/login/pages/UpdateEmail.tsx +26 -36
- package/src/login/pages/WebauthnAuthenticate.tsx +26 -32
- package/src/login/pages/WebauthnError.tsx +11 -22
- package/src/login/pages/WebauthnRegister.tsx +20 -28
- package/src/tools/clsx.ts +6 -48
- package/src/tools/clsx_withTransform.ts +55 -0
- package/src/vite-plugin/vite-plugin.ts +14 -6
- package/tools/clsx.d.ts +3 -2
- package/tools/clsx.js +5 -41
- package/tools/clsx.js.map +1 -1
- package/tools/clsx_withTransform.d.ts +5 -0
- package/tools/clsx_withTransform.js +43 -0
- package/tools/clsx_withTransform.js.map +1 -0
- package/vite-plugin/index.js +167 -37
- package/account/lib/useGetClassName.d.ts +0 -7
- package/account/lib/useGetClassName.js.map +0 -1
- package/lib/useGetClassName.d.ts +0 -10
- package/lib/useGetClassName.js +0 -14
- package/lib/useGetClassName.js.map +0 -1
- package/login/lib/useGetClassName.d.ts +0 -7
- package/login/lib/useGetClassName.js.map +0 -1
- package/src/lib/useGetClassName.ts +0 -27
@@ -1,24 +1,26 @@
|
|
1
1
|
import { useState } from "react";
|
2
2
|
import { clsx } from "keycloakify/tools/clsx";
|
3
|
-
import {
|
3
|
+
import { getKcClsx } from "keycloakify/account/lib/kcClsx";
|
4
4
|
import type { PageProps } from "keycloakify/account/pages/PageProps";
|
5
5
|
import type { KcContext } from "../KcContext";
|
6
|
-
import
|
6
|
+
import { useI18n } from "../i18n";
|
7
7
|
|
8
|
-
export default function Password(props: PageProps<Extract<KcContext, { pageId: "password.ftl" }
|
9
|
-
const { kcContext,
|
8
|
+
export default function Password(props: PageProps<Extract<KcContext, { pageId: "password.ftl" }>>) {
|
9
|
+
const { kcContext, doUseDefaultCss, Template } = props;
|
10
10
|
|
11
|
-
const
|
11
|
+
const classes = {
|
12
|
+
...props.classes,
|
13
|
+
kcBodyClass: clsx(props.classes?.kcBodyClass, "password")
|
14
|
+
};
|
15
|
+
|
16
|
+
const { kcClsx } = getKcClsx({
|
12
17
|
doUseDefaultCss,
|
13
|
-
classes
|
14
|
-
...classes,
|
15
|
-
kcBodyClass: clsx(classes?.kcBodyClass, "password")
|
16
|
-
}
|
18
|
+
classes
|
17
19
|
});
|
18
20
|
|
19
21
|
const { url, password, account, stateChecker } = kcContext;
|
20
22
|
|
21
|
-
const { msgStr, msg } =
|
23
|
+
const { msgStr, msg } = useI18n({ kcContext });
|
22
24
|
|
23
25
|
const [currentPassword, setCurrentPassword] = useState("");
|
24
26
|
const [newPassword, setNewPassword] = useState("");
|
@@ -75,7 +77,6 @@ export default function Password(props: PageProps<Extract<KcContext, { pageId: "
|
|
75
77
|
return kcContext.message;
|
76
78
|
})()
|
77
79
|
},
|
78
|
-
i18n,
|
79
80
|
doUseDefaultCss,
|
80
81
|
classes
|
81
82
|
}}
|
@@ -192,11 +193,7 @@ export default function Password(props: PageProps<Extract<KcContext, { pageId: "
|
|
192
193
|
<button
|
193
194
|
disabled={newPasswordError !== "" || newPasswordConfirmError !== ""}
|
194
195
|
type="submit"
|
195
|
-
className={
|
196
|
-
getClassName("kcButtonClass"),
|
197
|
-
getClassName("kcButtonPrimaryClass"),
|
198
|
-
getClassName("kcButtonLargeClass")
|
199
|
-
)}
|
196
|
+
className={kcClsx("kcButtonClass", "kcButtonPrimaryClass", "kcButtonLargeClass")}
|
200
197
|
name="submitAction"
|
201
198
|
value="Save"
|
202
199
|
>
|
@@ -1,23 +1,22 @@
|
|
1
|
-
import {
|
2
|
-
import { useGetClassName } from "keycloakify/account/lib/useGetClassName";
|
1
|
+
import { getKcClsx } from "keycloakify/account/lib/kcClsx";
|
3
2
|
import type { PageProps } from "keycloakify/account/pages/PageProps";
|
4
3
|
import type { KcContext } from "../KcContext";
|
5
|
-
import
|
4
|
+
import { useI18n } from "../i18n";
|
6
5
|
|
7
|
-
export default function Sessions(props: PageProps<Extract<KcContext, { pageId: "sessions.ftl" }
|
8
|
-
const { kcContext,
|
6
|
+
export default function Sessions(props: PageProps<Extract<KcContext, { pageId: "sessions.ftl" }>>) {
|
7
|
+
const { kcContext, doUseDefaultCss, Template, classes } = props;
|
9
8
|
|
10
|
-
const {
|
9
|
+
const { kcClsx } = getKcClsx({
|
11
10
|
doUseDefaultCss,
|
12
11
|
classes
|
13
12
|
});
|
14
13
|
|
15
14
|
const { url, stateChecker, sessions } = kcContext;
|
16
15
|
|
17
|
-
const { msg } =
|
16
|
+
const { msg } = useI18n({ kcContext });
|
18
17
|
return (
|
19
|
-
<Template {...{ kcContext,
|
20
|
-
<div className={
|
18
|
+
<Template {...{ kcContext, doUseDefaultCss, classes }} active="sessions">
|
19
|
+
<div className={kcClsx("kcContentWrapperClass")}>
|
21
20
|
<div className="col-md-10">
|
22
21
|
<h2>{msg("sessionsHtmlTitle")}</h2>
|
23
22
|
</div>
|
@@ -56,7 +55,7 @@ export default function Sessions(props: PageProps<Extract<KcContext, { pageId: "
|
|
56
55
|
|
57
56
|
<form action={url.sessionsUrl} method="post">
|
58
57
|
<input type="hidden" id="stateChecker" name="stateChecker" value={stateChecker} />
|
59
|
-
<button id="logout-all-sessions" type="submit" className={
|
58
|
+
<button id="logout-all-sessions" type="submit" className={kcClsx("kcButtonDefaultClass", "kcButtonClass")}>
|
60
59
|
{msg("doLogOutAllSessions")}
|
61
60
|
</button>
|
62
61
|
</form>
|
@@ -1,20 +1,20 @@
|
|
1
1
|
import { clsx } from "keycloakify/tools/clsx";
|
2
|
-
import {
|
2
|
+
import { getKcClsx } from "keycloakify/account/lib/kcClsx";
|
3
3
|
import type { PageProps } from "keycloakify/account/pages/PageProps";
|
4
4
|
import type { KcContext } from "../KcContext";
|
5
|
-
import
|
5
|
+
import { useI18n } from "../i18n";
|
6
6
|
|
7
|
-
export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp.ftl" }
|
8
|
-
const { kcContext,
|
7
|
+
export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp.ftl" }>>) {
|
8
|
+
const { kcContext, doUseDefaultCss, Template, classes } = props;
|
9
9
|
|
10
|
-
const {
|
10
|
+
const { kcClsx } = getKcClsx({
|
11
11
|
doUseDefaultCss,
|
12
12
|
classes
|
13
13
|
});
|
14
14
|
|
15
15
|
const { totp, mode, url, messagesPerField, stateChecker } = kcContext;
|
16
16
|
|
17
|
-
const { msg, msgStr, advancedMsg } =
|
17
|
+
const { msg, msgStr, advancedMsg } = useI18n({ kcContext });
|
18
18
|
|
19
19
|
const algToKeyUriAlg: Record<(typeof kcContext)["totp"]["policy"]["algorithm"], string> = {
|
20
20
|
HmacSHA1: "SHA1",
|
@@ -23,7 +23,7 @@ export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp
|
|
23
23
|
};
|
24
24
|
|
25
25
|
return (
|
26
|
-
<Template {...{ kcContext,
|
26
|
+
<Template {...{ kcContext, doUseDefaultCss, classes }} active="totp">
|
27
27
|
<>
|
28
28
|
<div className="row">
|
29
29
|
<div className="col-md-10">
|
@@ -140,9 +140,9 @@ export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp
|
|
140
140
|
</li>
|
141
141
|
</ol>
|
142
142
|
<hr />
|
143
|
-
<form action={url.totpUrl} className={
|
143
|
+
<form action={url.totpUrl} className={kcClsx("kcFormClass")} id="kc-totp-settings-form" method="post">
|
144
144
|
<input type="hidden" id="stateChecker" name="stateChecker" value={stateChecker} />
|
145
|
-
<div className={
|
145
|
+
<div className={kcClsx("kcFormGroupClass")}>
|
146
146
|
<div className="col-sm-2 col-md-2">
|
147
147
|
<label htmlFor="totp" className="control-label">
|
148
148
|
{msg("authenticatorCode")}
|
@@ -155,12 +155,12 @@ export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp
|
|
155
155
|
id="totp"
|
156
156
|
name="totp"
|
157
157
|
autoComplete="off"
|
158
|
-
className={
|
158
|
+
className={kcClsx("kcInputClass")}
|
159
159
|
aria-invalid={messagesPerField.existsError("totp")}
|
160
160
|
/>
|
161
161
|
|
162
162
|
{messagesPerField.existsError("totp") && (
|
163
|
-
<span id="input-error-otp-code" className={
|
163
|
+
<span id="input-error-otp-code" className={kcClsx("kcInputErrorMessageClass")} aria-live="polite">
|
164
164
|
{messagesPerField.get("totp")}
|
165
165
|
</span>
|
166
166
|
)}
|
@@ -169,9 +169,9 @@ export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp
|
|
169
169
|
{mode && <input type="hidden" id="mode" value={mode} />}
|
170
170
|
</div>
|
171
171
|
|
172
|
-
<div className={
|
172
|
+
<div className={kcClsx("kcFormGroupClass")}>
|
173
173
|
<div className="col-sm-2 col-md-2">
|
174
|
-
<label htmlFor="userLabel" className={
|
174
|
+
<label htmlFor="userLabel" className={kcClsx("kcLabelClass")}>
|
175
175
|
{msg("totpDeviceName")}
|
176
176
|
</label>
|
177
177
|
{totp.otpCredentials.length >= 1 && <span className="required">*</span>}
|
@@ -182,37 +182,28 @@ export default function Totp(props: PageProps<Extract<KcContext, { pageId: "totp
|
|
182
182
|
id="userLabel"
|
183
183
|
name="userLabel"
|
184
184
|
autoComplete="off"
|
185
|
-
className={
|
185
|
+
className={kcClsx("kcInputClass")}
|
186
186
|
aria-invalid={messagesPerField.existsError("userLabel")}
|
187
187
|
/>
|
188
188
|
{messagesPerField.existsError("userLabel") && (
|
189
|
-
<span id="input-error-otp-label" className={
|
189
|
+
<span id="input-error-otp-label" className={kcClsx("kcInputErrorMessageClass")} aria-live="polite">
|
190
190
|
{messagesPerField.get("userLabel")}
|
191
191
|
</span>
|
192
192
|
)}
|
193
193
|
</div>
|
194
194
|
</div>
|
195
195
|
|
196
|
-
<div id="kc-form-buttons" className={clsx(
|
197
|
-
<div className={
|
196
|
+
<div id="kc-form-buttons" className={clsx(kcClsx("kcFormGroupClass"), "text-right")}>
|
197
|
+
<div className={kcClsx("kcInputWrapperClass")}>
|
198
198
|
<input
|
199
199
|
type="submit"
|
200
|
-
className={
|
201
|
-
getClassName("kcButtonClass"),
|
202
|
-
getClassName("kcButtonPrimaryClass"),
|
203
|
-
getClassName("kcButtonLargeClass")
|
204
|
-
)}
|
200
|
+
className={kcClsx("kcButtonClass", "kcButtonPrimaryClass", "kcButtonLargeClass")}
|
205
201
|
id="saveTOTPBtn"
|
206
202
|
value={msgStr("doSave")}
|
207
203
|
/>
|
208
204
|
<button
|
209
205
|
type="submit"
|
210
|
-
className={
|
211
|
-
getClassName("kcButtonClass"),
|
212
|
-
getClassName("kcButtonDefaultClass"),
|
213
|
-
getClassName("kcButtonLargeClass"),
|
214
|
-
getClassName("kcButtonLargeClass")
|
215
|
-
)}
|
206
|
+
className={kcClsx("kcButtonClass", "kcButtonDefaultClass", "kcButtonLargeClass", "kcButtonLargeClass")}
|
216
207
|
id="cancelTOTPBtn"
|
217
208
|
name="submitAction"
|
218
209
|
value="Cancel"
|
@@ -8,6 +8,7 @@ import * as recast from "recast";
|
|
8
8
|
import * as babelParser from "@babel/parser";
|
9
9
|
import babelGenerate from "@babel/generator";
|
10
10
|
import * as babelTypes from "@babel/types";
|
11
|
+
import { escapeStringForPropertiesFile } from "../../tools/escapeStringForPropertiesFile";
|
11
12
|
|
12
13
|
export function generateMessageProperties(params: {
|
13
14
|
themeSrcDirPath: string;
|
@@ -146,7 +147,7 @@ export function generateMessageProperties(params: {
|
|
146
147
|
|
147
148
|
for (const [languageTag, keyValueMap] of Object.entries(keyValueMapByLanguageTag)) {
|
148
149
|
const propertiesFileSource = Object.entries(keyValueMap)
|
149
|
-
.map(([key, value]) => `${key}=${
|
150
|
+
.map(([key, value]) => `${key}=${escapeStringForPropertiesFile(value)}`)
|
150
151
|
.join("\n");
|
151
152
|
|
152
153
|
out.push({
|
@@ -164,68 +165,3 @@ export function generateMessageProperties(params: {
|
|
164
165
|
|
165
166
|
return out;
|
166
167
|
}
|
167
|
-
|
168
|
-
// Convert a JavaScript string to UTF-16 encoding
|
169
|
-
function toUTF16(codePoint: number): string {
|
170
|
-
if (codePoint <= 0xffff) {
|
171
|
-
// BMP character
|
172
|
-
return "\\u" + codePoint.toString(16).padStart(4, "0");
|
173
|
-
} else {
|
174
|
-
// Non-BMP character
|
175
|
-
codePoint -= 0x10000;
|
176
|
-
let highSurrogate = (codePoint >> 10) + 0xd800;
|
177
|
-
let lowSurrogate = (codePoint % 0x400) + 0xdc00;
|
178
|
-
return (
|
179
|
-
"\\u" +
|
180
|
-
highSurrogate.toString(16).padStart(4, "0") +
|
181
|
-
"\\u" +
|
182
|
-
lowSurrogate.toString(16).padStart(4, "0")
|
183
|
-
);
|
184
|
-
}
|
185
|
-
}
|
186
|
-
|
187
|
-
// Escapes special characters for use in a .properties file
|
188
|
-
function escapeString(str: string): string {
|
189
|
-
let escapedStr = "";
|
190
|
-
for (const char of [...str]) {
|
191
|
-
const codePoint = char.codePointAt(0);
|
192
|
-
if (!codePoint) continue;
|
193
|
-
|
194
|
-
switch (char) {
|
195
|
-
case "\n":
|
196
|
-
escapedStr += "\\n";
|
197
|
-
break;
|
198
|
-
case "\r":
|
199
|
-
escapedStr += "\\r";
|
200
|
-
break;
|
201
|
-
case "\t":
|
202
|
-
escapedStr += "\\t";
|
203
|
-
break;
|
204
|
-
case "\\":
|
205
|
-
escapedStr += "\\\\";
|
206
|
-
break;
|
207
|
-
case ":":
|
208
|
-
escapedStr += "\\:";
|
209
|
-
break;
|
210
|
-
case "=":
|
211
|
-
escapedStr += "\\=";
|
212
|
-
break;
|
213
|
-
case "#":
|
214
|
-
escapedStr += "\\#";
|
215
|
-
break;
|
216
|
-
case "!":
|
217
|
-
escapedStr += "\\!";
|
218
|
-
break;
|
219
|
-
case "'":
|
220
|
-
escapedStr += "''";
|
221
|
-
break;
|
222
|
-
default:
|
223
|
-
if (codePoint > 0x7f) {
|
224
|
-
escapedStr += toUTF16(codePoint); // Non-ASCII characters
|
225
|
-
} else {
|
226
|
-
escapedStr += char; // ASCII character needs no escape
|
227
|
-
}
|
228
|
-
}
|
229
|
-
}
|
230
|
-
return escapedStr;
|
231
|
-
}
|
package/src/bin/keycloakify/generateSrcMainResources/generateSrcMainResourcesForMainTheme.ts
CHANGED
@@ -38,6 +38,7 @@ import {
|
|
38
38
|
type MetaInfKeycloakTheme
|
39
39
|
} from "../../shared/metaInfKeycloakThemes";
|
40
40
|
import { objectEntries } from "tsafe/objectEntries";
|
41
|
+
import { escapeStringForPropertiesFile } from "../../tools/escapeStringForPropertiesFile";
|
41
42
|
|
42
43
|
export type BuildOptionsLike = BuildOptionsLike_kcContextExclusionsFtlCode &
|
43
44
|
BuildOptionsLike_downloadKeycloakStaticResources &
|
@@ -50,6 +51,7 @@ export type BuildOptionsLike = BuildOptionsLike_kcContextExclusionsFtlCode &
|
|
50
51
|
urlPathname: string | undefined;
|
51
52
|
reactAppRootDirPath: string;
|
52
53
|
keycloakifyBuildDirPath: string;
|
54
|
+
environmentVariables: { name: string; default: string }[];
|
53
55
|
};
|
54
56
|
|
55
57
|
assert<BuildOptions extends BuildOptionsLike ? true : false>();
|
@@ -261,7 +263,11 @@ export async function generateSrcMainResourcesForMainTheme(params: {
|
|
261
263
|
}
|
262
264
|
assert<Equals<typeof themeType, never>>(false);
|
263
265
|
})()}`,
|
264
|
-
...(buildOptions.extraThemeProperties ?? [])
|
266
|
+
...(buildOptions.extraThemeProperties ?? []),
|
267
|
+
buildOptions.environmentVariables.map(
|
268
|
+
({ name, default: defaultValue }) =>
|
269
|
+
`${name}=\${env.${name}:${escapeStringForPropertiesFile(defaultValue)}}`
|
270
|
+
)
|
265
271
|
].join("\n\n"),
|
266
272
|
"utf8"
|
267
273
|
)
|
package/src/bin/main.ts
CHANGED
@@ -205,6 +205,21 @@ program
|
|
205
205
|
}
|
206
206
|
});
|
207
207
|
|
208
|
+
program
|
209
|
+
.command({
|
210
|
+
name: "update-kc-gen",
|
211
|
+
description:
|
212
|
+
"(Webpack/Create-React-App only) Create/update the kc.gen.ts file in your project."
|
213
|
+
})
|
214
|
+
.task({
|
215
|
+
skip,
|
216
|
+
handler: async cliCommandOptions => {
|
217
|
+
const { command } = await import("./update-kc-gen");
|
218
|
+
|
219
|
+
await command({ cliCommandOptions });
|
220
|
+
}
|
221
|
+
});
|
222
|
+
|
208
223
|
// Fallback to build command if no command is provided
|
209
224
|
{
|
210
225
|
const [, , ...rest] = process.argv;
|
@@ -31,15 +31,17 @@ export type BuildOptions = {
|
|
31
31
|
assetsDirPath: string;
|
32
32
|
npmWorkspaceRootDirPath: string;
|
33
33
|
kcContextExclusionsFtlCode: string | undefined;
|
34
|
+
environmentVariables: { name: string; default: string }[];
|
34
35
|
};
|
35
36
|
|
36
37
|
export type UserProvidedBuildOptions = {
|
38
|
+
themeName?: string | string[];
|
39
|
+
environmentVariables?: { name: string; default: string }[];
|
37
40
|
extraThemeProperties?: string[];
|
38
41
|
artifactId?: string;
|
39
42
|
groupId?: string;
|
40
43
|
loginThemeResourcesFromKeycloakVersion?: string;
|
41
44
|
keycloakifyBuildDirPath?: string;
|
42
|
-
themeName?: string | string[];
|
43
45
|
kcContextExclusionsFtlCode?: string;
|
44
46
|
};
|
45
47
|
|
@@ -305,6 +307,7 @@ export function readBuildOptions(params: {
|
|
305
307
|
return pathJoin(reactAppBuildDirPath, resolvedViteConfig.assetsDir);
|
306
308
|
})(),
|
307
309
|
npmWorkspaceRootDirPath,
|
308
|
-
kcContextExclusionsFtlCode: userProvidedBuildOptions.kcContextExclusionsFtlCode
|
310
|
+
kcContextExclusionsFtlCode: userProvidedBuildOptions.kcContextExclusionsFtlCode,
|
311
|
+
environmentVariables: userProvidedBuildOptions.environmentVariables ?? []
|
309
312
|
};
|
310
313
|
}
|
@@ -0,0 +1,61 @@
|
|
1
|
+
import { assert } from "tsafe/assert";
|
2
|
+
import type { BuildOptions } from "./buildOptions";
|
3
|
+
import { getThemeSrcDirPath } from "./getThemeSrcDirPath";
|
4
|
+
import * as fs from "fs/promises";
|
5
|
+
import { join as pathJoin } from "path";
|
6
|
+
|
7
|
+
export type BuildOptionsLike = {
|
8
|
+
reactAppRootDirPath: string;
|
9
|
+
themeNames: string[];
|
10
|
+
environmentVariables: { name: string; default: string }[];
|
11
|
+
};
|
12
|
+
|
13
|
+
assert<BuildOptions extends BuildOptionsLike ? true : false>();
|
14
|
+
|
15
|
+
export async function generateKcGenTs(params: {
|
16
|
+
buildOptions: BuildOptionsLike;
|
17
|
+
}): Promise<void> {
|
18
|
+
const { buildOptions } = params;
|
19
|
+
|
20
|
+
const { themeSrcDirPath } = getThemeSrcDirPath({
|
21
|
+
reactAppRootDirPath: buildOptions.reactAppRootDirPath
|
22
|
+
});
|
23
|
+
|
24
|
+
await fs.writeFile(
|
25
|
+
pathJoin(themeSrcDirPath, "kc.gen.ts"),
|
26
|
+
Buffer.from(
|
27
|
+
[
|
28
|
+
`/* prettier-ignore-start */`,
|
29
|
+
``,
|
30
|
+
`/* eslint-disable */`,
|
31
|
+
``,
|
32
|
+
`// @ts-nocheck`,
|
33
|
+
``,
|
34
|
+
`// noinspection JSUnusedGlobalSymbols`,
|
35
|
+
``,
|
36
|
+
`// This file is auto-generated by Keycloakify`,
|
37
|
+
``,
|
38
|
+
`export type ThemeName = ${buildOptions.themeNames.map(themeName => `"${themeName}"`).join(" | ")};`,
|
39
|
+
``,
|
40
|
+
`export const themeNames: ThemeName[] = [${buildOptions.themeNames.map(themeName => `"${themeName}"`).join(", ")}];`,
|
41
|
+
``,
|
42
|
+
`export type KcEnvName = ${buildOptions.environmentVariables.length === 0 ? "never" : buildOptions.environmentVariables.map(({ name }) => `"${name}"`).join(" | ")};`,
|
43
|
+
``,
|
44
|
+
`export const KcEnvNames: KcEnvName[] = [${buildOptions.environmentVariables.map(({ name }) => `"${name}"`).join(", ")}];`,
|
45
|
+
``,
|
46
|
+
`export const kcEnvDefaults: Record<KcEnvName, string> = ${JSON.stringify(
|
47
|
+
Object.fromEntries(
|
48
|
+
buildOptions.environmentVariables.map(
|
49
|
+
({ name, default: defaultValue }) => [name, defaultValue]
|
50
|
+
)
|
51
|
+
),
|
52
|
+
null,
|
53
|
+
2
|
54
|
+
)};`,
|
55
|
+
``,
|
56
|
+
`/* prettier-ignore-end */`
|
57
|
+
].join("\n"),
|
58
|
+
"utf8"
|
59
|
+
)
|
60
|
+
);
|
61
|
+
}
|
@@ -0,0 +1,64 @@
|
|
1
|
+
// Convert a JavaScript string to UTF-16 encoding
|
2
|
+
function toUTF16(codePoint: number): string {
|
3
|
+
if (codePoint <= 0xffff) {
|
4
|
+
// BMP character
|
5
|
+
return "\\u" + codePoint.toString(16).padStart(4, "0");
|
6
|
+
} else {
|
7
|
+
// Non-BMP character
|
8
|
+
codePoint -= 0x10000;
|
9
|
+
let highSurrogate = (codePoint >> 10) + 0xd800;
|
10
|
+
let lowSurrogate = (codePoint % 0x400) + 0xdc00;
|
11
|
+
return (
|
12
|
+
"\\u" +
|
13
|
+
highSurrogate.toString(16).padStart(4, "0") +
|
14
|
+
"\\u" +
|
15
|
+
lowSurrogate.toString(16).padStart(4, "0")
|
16
|
+
);
|
17
|
+
}
|
18
|
+
}
|
19
|
+
|
20
|
+
// Escapes special characters for use in a .properties file
|
21
|
+
export function escapeStringForPropertiesFile(str: string): string {
|
22
|
+
let escapedStr = "";
|
23
|
+
for (const char of [...str]) {
|
24
|
+
const codePoint = char.codePointAt(0);
|
25
|
+
if (!codePoint) continue;
|
26
|
+
|
27
|
+
switch (char) {
|
28
|
+
case "\n":
|
29
|
+
escapedStr += "\\n";
|
30
|
+
break;
|
31
|
+
case "\r":
|
32
|
+
escapedStr += "\\r";
|
33
|
+
break;
|
34
|
+
case "\t":
|
35
|
+
escapedStr += "\\t";
|
36
|
+
break;
|
37
|
+
case "\\":
|
38
|
+
escapedStr += "\\\\";
|
39
|
+
break;
|
40
|
+
case ":":
|
41
|
+
escapedStr += "\\:";
|
42
|
+
break;
|
43
|
+
case "=":
|
44
|
+
escapedStr += "\\=";
|
45
|
+
break;
|
46
|
+
case "#":
|
47
|
+
escapedStr += "\\#";
|
48
|
+
break;
|
49
|
+
case "!":
|
50
|
+
escapedStr += "\\!";
|
51
|
+
break;
|
52
|
+
case "'":
|
53
|
+
escapedStr += "''";
|
54
|
+
break;
|
55
|
+
default:
|
56
|
+
if (codePoint > 0x7f) {
|
57
|
+
escapedStr += toUTF16(codePoint); // Non-ASCII characters
|
58
|
+
} else {
|
59
|
+
escapedStr += char; // ASCII character needs no escape
|
60
|
+
}
|
61
|
+
}
|
62
|
+
}
|
63
|
+
return escapedStr;
|
64
|
+
}
|
@@ -0,0 +1,13 @@
|
|
1
|
+
import type { CliCommandOptions } from "./main";
|
2
|
+
import { readBuildOptions } from "./shared/buildOptions";
|
3
|
+
import { generateKcGenTs } from "./shared/generateKcGenTs";
|
4
|
+
|
5
|
+
export async function command(params: { cliCommandOptions: CliCommandOptions }) {
|
6
|
+
const { cliCommandOptions } = params;
|
7
|
+
|
8
|
+
const buildOptions = readBuildOptions({
|
9
|
+
cliCommandOptions
|
10
|
+
});
|
11
|
+
|
12
|
+
await generateKcGenTs({ buildOptions });
|
13
|
+
}
|
@@ -0,0 +1,75 @@
|
|
1
|
+
import type { Param0 } from "tsafe";
|
2
|
+
import { type CxArg, clsx_withTransform } from "../tools/clsx_withTransform";
|
3
|
+
import { clsx } from "../tools/clsx";
|
4
|
+
import { assert } from "tsafe/assert";
|
5
|
+
import { is } from "tsafe/is";
|
6
|
+
|
7
|
+
export function createGetKcClsx<ClassKey extends string>(params: {
|
8
|
+
defaultClasses: Record<ClassKey, string | undefined>;
|
9
|
+
}) {
|
10
|
+
const { defaultClasses } = params;
|
11
|
+
|
12
|
+
function areSameParams(
|
13
|
+
params1: Param0<typeof getKcClsx>,
|
14
|
+
params2: Param0<typeof getKcClsx>
|
15
|
+
): boolean {
|
16
|
+
if (params1.doUseDefaultCss !== params2.doUseDefaultCss) {
|
17
|
+
return false;
|
18
|
+
}
|
19
|
+
|
20
|
+
if (params1.classes === params2.classes) {
|
21
|
+
return true;
|
22
|
+
}
|
23
|
+
|
24
|
+
return JSON.stringify(params1.classes) === JSON.stringify(params2.classes);
|
25
|
+
}
|
26
|
+
|
27
|
+
let cache:
|
28
|
+
| {
|
29
|
+
params: Param0<typeof getKcClsx>;
|
30
|
+
result: ReturnType<typeof getKcClsx>;
|
31
|
+
}
|
32
|
+
| undefined = undefined;
|
33
|
+
|
34
|
+
function getKcClsx(params: {
|
35
|
+
doUseDefaultCss: boolean;
|
36
|
+
classes: Partial<Record<ClassKey, string>> | undefined;
|
37
|
+
}): { kcClsx: (...args: CxArg<ClassKey>[]) => string } {
|
38
|
+
// NOTE: We implement a cache here only so that getClassName can be stable across renders.
|
39
|
+
// We don't want to use useConstCallback because we want this to be useable outside of React.
|
40
|
+
use_cache: {
|
41
|
+
if (cache === undefined) {
|
42
|
+
break use_cache;
|
43
|
+
}
|
44
|
+
|
45
|
+
if (!areSameParams(cache.params, params)) {
|
46
|
+
break use_cache;
|
47
|
+
}
|
48
|
+
|
49
|
+
return cache.result;
|
50
|
+
}
|
51
|
+
|
52
|
+
const { classes, doUseDefaultCss } = params;
|
53
|
+
|
54
|
+
function kcClsx(...args: CxArg<ClassKey>[]): string {
|
55
|
+
return clsx_withTransform({
|
56
|
+
args,
|
57
|
+
transform: classKey => {
|
58
|
+
assert(is<ClassKey>(classKey));
|
59
|
+
|
60
|
+
return clsx(
|
61
|
+
classKey,
|
62
|
+
doUseDefaultCss ? defaultClasses[classKey] : undefined,
|
63
|
+
classes?.[classKey]
|
64
|
+
);
|
65
|
+
}
|
66
|
+
});
|
67
|
+
}
|
68
|
+
|
69
|
+
cache = { params, result: { kcClsx } };
|
70
|
+
|
71
|
+
return { kcClsx };
|
72
|
+
}
|
73
|
+
|
74
|
+
return { getKcClsx };
|
75
|
+
}
|
package/src/login/Fallback.tsx
CHANGED
@@ -3,7 +3,6 @@ import { assert, type Equals } from "tsafe/assert";
|
|
3
3
|
import type { LazyOrNot } from "keycloakify/tools/LazyOrNot";
|
4
4
|
import type { PageProps } from "keycloakify/login/pages/PageProps";
|
5
5
|
import type { KcContext } from "./KcContext";
|
6
|
-
import type { I18n } from "./i18n";
|
7
6
|
import type { UserProfileFormFieldsProps } from "keycloakify/login/UserProfileFormFields";
|
8
7
|
|
9
8
|
const Login = lazy(() => import("keycloakify/login/pages/Login"));
|
@@ -41,7 +40,7 @@ const LoginResetOtp = lazy(() => import("keycloakify/login/pages/LoginResetOtp")
|
|
41
40
|
const LoginX509Info = lazy(() => import("keycloakify/login/pages/LoginX509Info"));
|
42
41
|
const WebauthnError = lazy(() => import("keycloakify/login/pages/WebauthnError"));
|
43
42
|
|
44
|
-
type FallbackProps = PageProps<KcContext
|
43
|
+
type FallbackProps = PageProps<KcContext> & {
|
45
44
|
UserProfileFormFields: LazyOrNot<(props: UserProfileFormFieldsProps) => JSX.Element>;
|
46
45
|
};
|
47
46
|
|
@@ -10,20 +10,20 @@ import type { Equals } from "tsafe";
|
|
10
10
|
import type { MessageKey } from "../i18n/i18n";
|
11
11
|
|
12
12
|
export type ExtendKcContext<
|
13
|
-
|
14
|
-
|
13
|
+
KcContextExtension extends { properties?: Record<string, string | undefined> },
|
14
|
+
KcContextExtensionPerPage extends Record<string, Record<string, unknown>>
|
15
15
|
> = ValueOf<{
|
16
|
-
[PageId in keyof
|
16
|
+
[PageId in keyof KcContextExtensionPerPage | KcContext["pageId"]]: Extract<
|
17
17
|
KcContext,
|
18
18
|
{ pageId: PageId }
|
19
19
|
> extends never
|
20
20
|
? KcContext.Common &
|
21
|
-
|
21
|
+
KcContextExtension & {
|
22
22
|
pageId: PageId;
|
23
|
-
} &
|
23
|
+
} & KcContextExtensionPerPage[PageId]
|
24
24
|
: Extract<KcContext, { pageId: PageId }> &
|
25
|
-
|
26
|
-
|
25
|
+
KcContextExtension &
|
26
|
+
KcContextExtensionPerPage[PageId];
|
27
27
|
}>;
|
28
28
|
|
29
29
|
/** Take theses type definition with a grain of salt.
|