keycloakify 9.4.0-rc.9 → 9.4.1
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/README.md +4 -0
- package/account/i18n/baseMessages/index.d.ts +358 -0
- package/account/i18n/baseMessages/index.js +2 -1
- package/account/i18n/baseMessages/index.js.map +1 -1
- package/account/pages/PageProps.d.ts +3 -2
- package/bin/constants.d.ts +1 -1
- package/bin/constants.js +1 -1
- package/bin/constants.js.map +1 -1
- package/bin/copy-keycloak-resources-to-public.d.ts +13 -1
- package/bin/copy-keycloak-resources-to-public.js +134 -68
- package/bin/copy-keycloak-resources-to-public.js.map +1 -1
- package/bin/download-builtin-keycloak-theme.d.ts +1 -0
- package/bin/download-builtin-keycloak-theme.js +2 -3
- package/bin/download-builtin-keycloak-theme.js.map +1 -1
- package/bin/{tools/downloadAndUnzip.d.ts → downloadAndUnzip.d.ts} +6 -6
- package/bin/downloadAndUnzip.js +255 -0
- package/bin/downloadAndUnzip.js.map +1 -0
- package/bin/eject-keycloak-page.js +6 -3
- package/bin/eject-keycloak-page.js.map +1 -1
- package/bin/keycloakify/buildOptions/buildOptions.d.ts +1 -0
- package/bin/keycloakify/buildOptions/buildOptions.js +54 -39
- package/bin/keycloakify/buildOptions/buildOptions.js.map +1 -1
- package/bin/keycloakify/buildOptions/getCacheDirPath.d.ts +5 -0
- package/bin/keycloakify/buildOptions/getCacheDirPath.js +22 -0
- package/bin/keycloakify/buildOptions/getCacheDirPath.js.map +1 -0
- package/bin/keycloakify/buildOptions/getNpmWorkspaceRootDirPath.d.ts +5 -0
- package/bin/keycloakify/buildOptions/getNpmWorkspaceRootDirPath.js +86 -0
- package/bin/keycloakify/buildOptions/getNpmWorkspaceRootDirPath.js.map +1 -0
- package/bin/keycloakify/buildOptions/getReactAppRootDirPath.d.ts +5 -0
- package/bin/keycloakify/buildOptions/getReactAppRootDirPath.js +26 -0
- package/bin/keycloakify/buildOptions/getReactAppRootDirPath.js.map +1 -0
- package/bin/keycloakify/buildOptions/resolvedViteConfig.d.ts +3 -4
- package/bin/keycloakify/buildOptions/resolvedViteConfig.js +4 -11
- package/bin/keycloakify/buildOptions/resolvedViteConfig.js.map +1 -1
- package/bin/keycloakify/generateTheme/bringInAccountV1.d.ts +1 -0
- package/bin/keycloakify/generateTheme/bringInAccountV1.js.map +1 -1
- package/bin/keycloakify/generateTheme/downloadKeycloakStaticResources.d.ts +1 -0
- package/bin/keycloakify/generateTheme/downloadKeycloakStaticResources.js.map +1 -1
- package/bin/keycloakify/generateTheme/generateTheme.d.ts +1 -0
- package/bin/keycloakify/generateTheme/generateTheme.js +7 -3
- package/bin/keycloakify/generateTheme/generateTheme.js.map +1 -1
- package/bin/keycloakify/keycloakify.js +8 -12
- package/bin/keycloakify/keycloakify.js.map +1 -1
- package/bin/tools/fetchProxyOptions.d.ts +5 -0
- package/bin/tools/fetchProxyOptions.js +172 -0
- package/bin/tools/fetchProxyOptions.js.map +1 -0
- package/bin/tools/fs.existsAsync.d.ts +1 -0
- package/bin/tools/fs.existsAsync.js +86 -0
- package/bin/tools/fs.existsAsync.js.map +1 -0
- package/bin/tools/getThisCodebaseRootDirPath.d.ts +1 -0
- package/bin/tools/{getProjectRoot.js → getThisCodebaseRootDirPath.js} +7 -7
- package/bin/tools/getThisCodebaseRootDirPath.js.map +1 -0
- package/bin/tools/grant-exec-perms.js +6 -4
- package/bin/tools/grant-exec-perms.js.map +1 -1
- package/bin/tools/readThisNpmProjectVersion.d.ts +1 -0
- package/bin/tools/readThisNpmProjectVersion.js +37 -0
- package/bin/tools/readThisNpmProjectVersion.js.map +1 -0
- package/lib/isStorybook.js +1 -2
- package/lib/isStorybook.js.map +1 -1
- package/login/i18n/baseMessages/index.d.ts +458 -0
- package/login/i18n/baseMessages/index.js +2 -1
- package/login/i18n/baseMessages/index.js.map +1 -1
- package/login/pages/PageProps.d.ts +3 -2
- package/package.json +41 -19
- package/src/account/i18n/baseMessages/index.ts +2 -1
- package/src/account/pages/PageProps.ts +3 -2
- package/src/bin/constants.ts +1 -1
- package/src/bin/copy-keycloak-resources-to-public.ts +75 -9
- package/src/bin/download-builtin-keycloak-theme.ts +3 -3
- package/src/bin/downloadAndUnzip.ts +203 -0
- package/src/bin/eject-keycloak-page.ts +6 -3
- package/src/bin/keycloakify/buildOptions/buildOptions.ts +28 -39
- package/src/bin/keycloakify/buildOptions/getCacheDirPath.ts +25 -0
- package/src/bin/keycloakify/buildOptions/getNpmWorkspaceRootDirPath.ts +49 -0
- package/src/bin/keycloakify/buildOptions/getReactAppRootDirPath.ts +23 -0
- package/src/bin/keycloakify/buildOptions/resolvedViteConfig.ts +7 -21
- package/src/bin/keycloakify/generateTheme/bringInAccountV1.ts +1 -0
- package/src/bin/keycloakify/generateTheme/downloadKeycloakStaticResources.ts +1 -0
- package/src/bin/keycloakify/generateTheme/generateTheme.ts +9 -2
- package/src/bin/keycloakify/keycloakify.ts +8 -14
- package/src/bin/tools/fetchProxyOptions.ts +73 -0
- package/src/bin/tools/fs.existsAsync.ts +11 -0
- package/src/bin/tools/{getProjectRoot.ts → getThisCodebaseRootDirPath.ts} +4 -4
- package/src/bin/tools/grant-exec-perms.ts +5 -3
- package/src/bin/tools/readThisNpmProjectVersion.ts +12 -0
- package/src/lib/isStorybook.ts +1 -3
- package/src/login/i18n/baseMessages/index.ts +2 -1
- package/src/login/pages/PageProps.ts +3 -2
- package/src/vite-plugin/vite-plugin.ts +48 -25
- package/vite-plugin/tsconfig.tsbuildinfo +1 -1
- package/vite-plugin/vite-plugin.d.ts +1 -2
- package/vite-plugin/vite-plugin.js +35 -20
- package/vite-plugin/vite-plugin.js.map +1 -1
- package/bin/keycloakify/buildOptions/getKeycloakifyBuildDirPath.d.ts +0 -7
- package/bin/keycloakify/buildOptions/getKeycloakifyBuildDirPath.js +0 -27
- package/bin/keycloakify/buildOptions/getKeycloakifyBuildDirPath.js.map +0 -1
- package/bin/tools/downloadAndUnzip.js +0 -445
- package/bin/tools/downloadAndUnzip.js.map +0 -1
- package/bin/tools/getProjectRoot.d.ts +0 -1
- package/bin/tools/getProjectRoot.js.map +0 -1
- package/src/bin/keycloakify/buildOptions/getKeycloakifyBuildDirPath.ts +0 -33
- package/src/bin/tools/downloadAndUnzip.ts +0 -301
- package/src/vite-plugin/config.json +0 -232
@@ -5,7 +5,6 @@ import { z } from "zod";
|
|
5
5
|
import { join as pathJoin } from "path";
|
6
6
|
import { resolvedViteConfigJsonBasename } from "../../constants";
|
7
7
|
import type { OptionalIfCanBeUndefined } from "../../tools/OptionalIfCanBeUndefined";
|
8
|
-
import { getKeycloakifyBuildDirPath } from "./getKeycloakifyBuildDirPath";
|
9
8
|
|
10
9
|
export type ResolvedViteConfig = {
|
11
10
|
buildDir: string;
|
@@ -28,31 +27,18 @@ const zResolvedViteConfig = z.object({
|
|
28
27
|
assert<Equals<Got, Expected>>();
|
29
28
|
}
|
30
29
|
|
31
|
-
export function readResolvedViteConfig(params: {
|
32
|
-
|
33
|
-
|
34
|
-
}
|
35
|
-
| {
|
36
|
-
resolvedViteConfig: ResolvedViteConfig;
|
37
|
-
}
|
38
|
-
| undefined {
|
39
|
-
const { reactAppRootDirPath, parsedPackageJson_keycloakify_keycloakifyBuildDirPath } = params;
|
30
|
+
export function readResolvedViteConfig(params: { cacheDirPath: string }): {
|
31
|
+
resolvedViteConfig: ResolvedViteConfig | undefined;
|
32
|
+
} {
|
33
|
+
const { cacheDirPath } = params;
|
40
34
|
|
41
|
-
const
|
35
|
+
const resolvedViteConfigJsonFilePath = pathJoin(cacheDirPath, resolvedViteConfigJsonBasename);
|
42
36
|
|
43
|
-
if (!fs.existsSync(
|
44
|
-
return undefined;
|
37
|
+
if (!fs.existsSync(resolvedViteConfigJsonFilePath)) {
|
38
|
+
return { "resolvedViteConfig": undefined };
|
45
39
|
}
|
46
40
|
|
47
|
-
const { keycloakifyBuildDirPath } = getKeycloakifyBuildDirPath({
|
48
|
-
reactAppRootDirPath,
|
49
|
-
parsedPackageJson_keycloakify_keycloakifyBuildDirPath,
|
50
|
-
"bundler": "vite"
|
51
|
-
});
|
52
|
-
|
53
41
|
const resolvedViteConfig = (() => {
|
54
|
-
const resolvedViteConfigJsonFilePath = pathJoin(keycloakifyBuildDirPath, resolvedViteConfigJsonBasename);
|
55
|
-
|
56
42
|
if (!fs.existsSync(resolvedViteConfigJsonFilePath)) {
|
57
43
|
throw new Error("Missing Keycloakify Vite plugin output.");
|
58
44
|
}
|
@@ -20,6 +20,7 @@ import { readFieldNameUsage } from "./readFieldNameUsage";
|
|
20
20
|
import { readExtraPagesNames } from "./readExtraPageNames";
|
21
21
|
import { generateMessageProperties } from "./generateMessageProperties";
|
22
22
|
import { bringInAccountV1 } from "./bringInAccountV1";
|
23
|
+
import { rmSync } from "../../tools/fs.rmSync";
|
23
24
|
|
24
25
|
export type BuildOptionsLike = {
|
25
26
|
bundler: "vite" | "webpack";
|
@@ -33,6 +34,7 @@ export type BuildOptionsLike = {
|
|
33
34
|
urlPathname: string | undefined;
|
34
35
|
doBuildRetrocompatAccountTheme: boolean;
|
35
36
|
themeNames: string[];
|
37
|
+
npmWorkspaceRootDirPath: string;
|
36
38
|
};
|
37
39
|
|
38
40
|
assert<BuildOptions extends BuildOptionsLike ? true : false>();
|
@@ -77,6 +79,11 @@ export async function generateTheme(params: {
|
|
77
79
|
const themeTypeDirPath = getThemeTypeDirPath({ themeType });
|
78
80
|
|
79
81
|
apply_replacers_and_move_to_theme_resources: {
|
82
|
+
const destDirPath = pathJoin(themeTypeDirPath, "resources", basenameOfTheKeycloakifyResourcesDir);
|
83
|
+
|
84
|
+
// NOTE: Prevent accumulation of files in the assets dir, as names are hashed they pile up.
|
85
|
+
rmSync(destDirPath, { "recursive": true, "force": true });
|
86
|
+
|
80
87
|
if (themeType === "account" && implementedThemeTypes.login) {
|
81
88
|
// NOTE: We prevend doing it twice, it has been done for the login theme.
|
82
89
|
|
@@ -88,7 +95,7 @@ export async function generateTheme(params: {
|
|
88
95
|
"resources",
|
89
96
|
basenameOfTheKeycloakifyResourcesDir
|
90
97
|
),
|
91
|
-
|
98
|
+
destDirPath
|
92
99
|
});
|
93
100
|
|
94
101
|
break apply_replacers_and_move_to_theme_resources;
|
@@ -96,7 +103,7 @@ export async function generateTheme(params: {
|
|
96
103
|
|
97
104
|
transformCodebase({
|
98
105
|
"srcDirPath": buildOptions.reactAppBuildDirPath,
|
99
|
-
|
106
|
+
destDirPath,
|
100
107
|
"transformSourceCode": ({ filePath, sourceCode }) => {
|
101
108
|
//NOTE: Prevent cycles, excludes the folder we generated for debug in public/
|
102
109
|
// This should not happen if users follow the new instruction setup but we keep it for retrocompatibility.
|
@@ -6,9 +6,9 @@ import { generateStartKeycloakTestingContainer } from "./generateStartKeycloakTe
|
|
6
6
|
import * as fs from "fs";
|
7
7
|
import { readBuildOptions } from "./buildOptions";
|
8
8
|
import { getLogger } from "../tools/logger";
|
9
|
-
import { assert } from "tsafe/assert";
|
10
9
|
import { getThemeSrcDirPath } from "../getThemeSrcDirPath";
|
11
|
-
import {
|
10
|
+
import { getThisCodebaseRootDirPath } from "../tools/getThisCodebaseRootDirPath";
|
11
|
+
import { readThisNpmProjectVersion } from "../tools/readThisNpmProjectVersion";
|
12
12
|
|
13
13
|
export async function main() {
|
14
14
|
const buildOptions = readBuildOptions({
|
@@ -18,23 +18,15 @@ export async function main() {
|
|
18
18
|
const logger = getLogger({ "isSilent": buildOptions.isSilent });
|
19
19
|
logger.log("🔏 Building the keycloak theme...⌚");
|
20
20
|
|
21
|
-
const keycloakifyDirPath = getProjectRoot();
|
22
|
-
|
23
21
|
const { themeSrcDirPath } = getThemeSrcDirPath({ "reactAppRootDirPath": buildOptions.reactAppRootDirPath });
|
24
22
|
|
25
23
|
for (const themeName of buildOptions.themeNames) {
|
26
24
|
await generateTheme({
|
27
25
|
themeName,
|
28
26
|
themeSrcDirPath,
|
29
|
-
"keycloakifySrcDirPath": pathJoin(
|
30
|
-
|
31
|
-
|
32
|
-
const version = JSON.parse(fs.readFileSync(pathJoin(keycloakifyDirPath, "package.json")).toString("utf8"))["version"];
|
33
|
-
|
34
|
-
assert(typeof version === "string");
|
35
|
-
|
36
|
-
return version;
|
37
|
-
})()
|
27
|
+
"keycloakifySrcDirPath": pathJoin(getThisCodebaseRootDirPath(), "src"),
|
28
|
+
"keycloakifyVersion": readThisNpmProjectVersion(),
|
29
|
+
buildOptions
|
38
30
|
});
|
39
31
|
}
|
40
32
|
|
@@ -67,7 +59,7 @@ export async function main() {
|
|
67
59
|
);
|
68
60
|
}
|
69
61
|
|
70
|
-
const containerKeycloakVersion = "23.0.
|
62
|
+
const containerKeycloakVersion = "23.0.6";
|
71
63
|
|
72
64
|
generateStartKeycloakTestingContainer({
|
73
65
|
"keycloakVersion": containerKeycloakVersion,
|
@@ -75,6 +67,8 @@ export async function main() {
|
|
75
67
|
buildOptions
|
76
68
|
});
|
77
69
|
|
70
|
+
fs.writeFileSync(pathJoin(buildOptions.keycloakifyBuildDirPath, ".gitignore"), Buffer.from("*", "utf8"));
|
71
|
+
|
78
72
|
logger.log(
|
79
73
|
[
|
80
74
|
"",
|
@@ -0,0 +1,73 @@
|
|
1
|
+
import { exec as execCallback } from "child_process";
|
2
|
+
import { readFile } from "fs/promises";
|
3
|
+
import { type FetchOptions } from "make-fetch-happen";
|
4
|
+
import { promisify } from "util";
|
5
|
+
|
6
|
+
function ensureArray<T>(arg0: T | T[]) {
|
7
|
+
return Array.isArray(arg0) ? arg0 : typeof arg0 === "undefined" ? [] : [arg0];
|
8
|
+
}
|
9
|
+
|
10
|
+
function ensureSingleOrNone<T>(arg0: T | T[]) {
|
11
|
+
if (!Array.isArray(arg0)) return arg0;
|
12
|
+
if (arg0.length === 0) return undefined;
|
13
|
+
if (arg0.length === 1) return arg0[0];
|
14
|
+
throw new Error("Illegal configuration, expected a single value but found multiple: " + arg0.map(String).join(", "));
|
15
|
+
}
|
16
|
+
|
17
|
+
type NPMConfig = Record<string, string | string[]>;
|
18
|
+
|
19
|
+
/**
|
20
|
+
* Get npm configuration as map
|
21
|
+
*/
|
22
|
+
async function getNmpConfig(params: { npmWorkspaceRootDirPath: string }) {
|
23
|
+
const { npmWorkspaceRootDirPath } = params;
|
24
|
+
|
25
|
+
const exec = promisify(execCallback);
|
26
|
+
|
27
|
+
const stdout = await exec("npm config get", { "encoding": "utf8", "cwd": npmWorkspaceRootDirPath }).then(({ stdout }) => stdout);
|
28
|
+
|
29
|
+
const npmConfigReducer = (cfg: NPMConfig, [key, value]: [string, string]) =>
|
30
|
+
key in cfg ? { ...cfg, [key]: [...ensureArray(cfg[key]), value] } : { ...cfg, [key]: value };
|
31
|
+
|
32
|
+
return stdout
|
33
|
+
.split("\n")
|
34
|
+
.filter(line => !line.startsWith(";"))
|
35
|
+
.map(line => line.trim())
|
36
|
+
.map(line => line.split("=", 2) as [string, string])
|
37
|
+
.reduce(npmConfigReducer, {} as NPMConfig);
|
38
|
+
}
|
39
|
+
|
40
|
+
export type ProxyFetchOptions = Pick<FetchOptions, "proxy" | "noProxy" | "strictSSL" | "cert" | "ca">;
|
41
|
+
|
42
|
+
export async function getProxyFetchOptions(params: { npmWorkspaceRootDirPath: string }): Promise<ProxyFetchOptions> {
|
43
|
+
const { npmWorkspaceRootDirPath } = params;
|
44
|
+
|
45
|
+
const cfg = await getNmpConfig({ npmWorkspaceRootDirPath });
|
46
|
+
|
47
|
+
const proxy = ensureSingleOrNone(cfg["https-proxy"] ?? cfg["proxy"]);
|
48
|
+
const noProxy = cfg["noproxy"] ?? cfg["no-proxy"];
|
49
|
+
|
50
|
+
function maybeBoolean(arg0: string | undefined) {
|
51
|
+
return typeof arg0 === "undefined" ? undefined : Boolean(arg0);
|
52
|
+
}
|
53
|
+
|
54
|
+
const strictSSL = maybeBoolean(ensureSingleOrNone(cfg["strict-ssl"]));
|
55
|
+
const cert = cfg["cert"];
|
56
|
+
const ca = ensureArray(cfg["ca"] ?? cfg["ca[]"]);
|
57
|
+
const cafile = ensureSingleOrNone(cfg["cafile"]);
|
58
|
+
|
59
|
+
if (typeof cafile !== "undefined" && cafile !== "null") {
|
60
|
+
ca.push(
|
61
|
+
...(await (async () => {
|
62
|
+
function chunks<T>(arr: T[], size: number = 2) {
|
63
|
+
return arr.map((_, i) => i % size == 0 && arr.slice(i, i + size)).filter(Boolean) as T[][];
|
64
|
+
}
|
65
|
+
|
66
|
+
const cafileContent = await readFile(cafile, "utf-8");
|
67
|
+
return chunks(cafileContent.split(/(-----END CERTIFICATE-----)/), 2).map(ca => ca.join("").replace(/^\n/, "").replace(/\n/g, "\\n"));
|
68
|
+
})())
|
69
|
+
);
|
70
|
+
}
|
71
|
+
|
72
|
+
return { proxy, noProxy, strictSSL, cert, "ca": ca.length === 0 ? undefined : ca };
|
73
|
+
}
|
@@ -1,19 +1,19 @@
|
|
1
1
|
import * as fs from "fs";
|
2
2
|
import * as path from "path";
|
3
3
|
|
4
|
-
function
|
4
|
+
function getThisCodebaseRootDirPath_rec(dirPath: string): string {
|
5
5
|
if (fs.existsSync(path.join(dirPath, "package.json"))) {
|
6
6
|
return dirPath;
|
7
7
|
}
|
8
|
-
return
|
8
|
+
return getThisCodebaseRootDirPath_rec(path.join(dirPath, ".."));
|
9
9
|
}
|
10
10
|
|
11
11
|
let result: string | undefined = undefined;
|
12
12
|
|
13
|
-
export function
|
13
|
+
export function getThisCodebaseRootDirPath(): string {
|
14
14
|
if (result !== undefined) {
|
15
15
|
return result;
|
16
16
|
}
|
17
17
|
|
18
|
-
return (result =
|
18
|
+
return (result = getThisCodebaseRootDirPath_rec(__dirname));
|
19
19
|
}
|
@@ -1,13 +1,15 @@
|
|
1
|
-
import {
|
1
|
+
import { getThisCodebaseRootDirPath } from "./getThisCodebaseRootDirPath";
|
2
2
|
import { join as pathJoin } from "path";
|
3
3
|
import { constants } from "fs";
|
4
4
|
import { chmod, stat } from "fs/promises";
|
5
5
|
|
6
6
|
(async () => {
|
7
|
-
const
|
7
|
+
const thisCodebaseRootDirPath = getThisCodebaseRootDirPath();
|
8
|
+
|
9
|
+
const { bin } = await import(pathJoin(thisCodebaseRootDirPath, "package.json"));
|
8
10
|
|
9
11
|
const promises = Object.values<string>(bin).map(async scriptPath => {
|
10
|
-
const fullPath = pathJoin(
|
12
|
+
const fullPath = pathJoin(thisCodebaseRootDirPath, scriptPath);
|
11
13
|
const oldMode = (await stat(fullPath)).mode;
|
12
14
|
const newMode = oldMode | constants.S_IXUSR | constants.S_IXGRP | constants.S_IXOTH;
|
13
15
|
await chmod(fullPath, newMode);
|
@@ -0,0 +1,12 @@
|
|
1
|
+
import { getThisCodebaseRootDirPath } from "./getThisCodebaseRootDirPath";
|
2
|
+
import { assert } from "tsafe/assert";
|
3
|
+
import * as fs from "fs";
|
4
|
+
import { join as pathJoin } from "path";
|
5
|
+
|
6
|
+
export function readThisNpmProjectVersion(): string {
|
7
|
+
const version = JSON.parse(fs.readFileSync(pathJoin(getThisCodebaseRootDirPath(), "package.json")).toString("utf8"))["version"];
|
8
|
+
|
9
|
+
assert(typeof version === "string");
|
10
|
+
|
11
|
+
return version;
|
12
|
+
}
|
package/src/lib/isStorybook.ts
CHANGED
@@ -1,16 +1,17 @@
|
|
1
1
|
//This code was automatically generated by running scripts/generate-i18n-messages.ts
|
2
2
|
//PLEASE DO NOT EDIT MANUALLY
|
3
|
+
import * as en from "./en";
|
3
4
|
|
4
5
|
export async function getMessages(currentLanguageTag: string) {
|
5
6
|
const { default: messages } = await (() => {
|
6
7
|
switch (currentLanguageTag) {
|
8
|
+
case "en": return en;
|
7
9
|
case "ar": return import("./ar");
|
8
10
|
case "ca": return import("./ca");
|
9
11
|
case "cs": return import("./cs");
|
10
12
|
case "da": return import("./da");
|
11
13
|
case "de": return import("./de");
|
12
14
|
case "el": return import("./el");
|
13
|
-
case "en": return import("./en");
|
14
15
|
case "es": return import("./es");
|
15
16
|
case "fa": return import("./fa");
|
16
17
|
case "fi": return import("./fi");
|
@@ -1,10 +1,11 @@
|
|
1
1
|
import type { I18n } from "keycloakify/login/i18n";
|
2
2
|
import { type TemplateProps, type ClassKey } from "keycloakify/login/TemplateProps";
|
3
3
|
import type { LazyOrNot } from "keycloakify/tools/LazyOrNot";
|
4
|
+
import type { KcContext } from "keycloakify/account/kcContext";
|
4
5
|
|
5
|
-
export type PageProps<KcContext, I18nExtended extends I18n> = {
|
6
|
+
export type PageProps<NarowedKcContext = KcContext, I18nExtended extends I18n = I18n> = {
|
6
7
|
Template: LazyOrNot<(props: TemplateProps<any, any>) => JSX.Element | null>;
|
7
|
-
kcContext:
|
8
|
+
kcContext: NarowedKcContext;
|
8
9
|
i18n: I18nExtended;
|
9
10
|
doUseDefaultCss: boolean;
|
10
11
|
classes?: Partial<Record<ClassKey, string>>;
|
@@ -1,28 +1,39 @@
|
|
1
1
|
import { join as pathJoin, relative as pathRelative, sep as pathSep } from "path";
|
2
|
-
import { readParsedPackageJson } from "../bin/keycloakify/buildOptions/parsedPackageJson";
|
3
2
|
import type { Plugin } from "vite";
|
4
|
-
import { assert } from "tsafe/assert";
|
5
3
|
import * as fs from "fs";
|
6
4
|
import { resolvedViteConfigJsonBasename, nameOfTheGlobal, basenameOfTheKeycloakifyResourcesDir, keycloak_resources } from "../bin/constants";
|
7
5
|
import type { ResolvedViteConfig } from "../bin/keycloakify/buildOptions/resolvedViteConfig";
|
8
|
-
import {
|
6
|
+
import { getCacheDirPath } from "../bin/keycloakify/buildOptions/getCacheDirPath";
|
9
7
|
import { replaceAll } from "../bin/tools/String.prototype.replaceAll";
|
10
8
|
import { id } from "tsafe/id";
|
11
9
|
import { rm } from "../bin/tools/fs.rm";
|
10
|
+
import { copyKeycloakResourcesToPublic } from "../bin/copy-keycloak-resources-to-public";
|
11
|
+
import { assert } from "tsafe/assert";
|
12
12
|
|
13
|
-
export function keycloakify()
|
13
|
+
export function keycloakify() {
|
14
14
|
let reactAppRootDirPath: string | undefined = undefined;
|
15
15
|
let urlPathname: string | undefined = undefined;
|
16
16
|
let buildDirPath: string | undefined = undefined;
|
17
|
+
let command: "build" | "serve" | undefined = undefined;
|
18
|
+
|
19
|
+
const plugin = {
|
20
|
+
"name": "keycloakify" as const,
|
21
|
+
"configResolved": async resolvedConfig => {
|
22
|
+
command = resolvedConfig.command;
|
17
23
|
|
18
|
-
return {
|
19
|
-
"name": "keycloakify",
|
20
|
-
"apply": "build",
|
21
|
-
"configResolved": resolvedConfig => {
|
22
24
|
reactAppRootDirPath = resolvedConfig.root;
|
23
25
|
urlPathname = (() => {
|
24
26
|
let out = resolvedConfig.env.BASE_URL;
|
25
27
|
|
28
|
+
if (out.startsWith(".") && command === "build") {
|
29
|
+
throw new Error(
|
30
|
+
[
|
31
|
+
`BASE_URL=${out} is not supported By Keycloakify. Use an absolute URL instead.`,
|
32
|
+
`If this is a problem, please open an issue at https://github.com/keycloakify/keycloakify/issues/new`
|
33
|
+
].join("\n")
|
34
|
+
);
|
35
|
+
}
|
36
|
+
|
26
37
|
if (out === undefined) {
|
27
38
|
return undefined;
|
28
39
|
}
|
@@ -40,19 +51,16 @@ export function keycloakify(): Plugin {
|
|
40
51
|
|
41
52
|
buildDirPath = pathJoin(reactAppRootDirPath, resolvedConfig.build.outDir);
|
42
53
|
|
43
|
-
const {
|
44
|
-
|
45
|
-
?.keycloakifyBuildDirPath,
|
46
|
-
reactAppRootDirPath,
|
47
|
-
"bundler": "vite"
|
54
|
+
const { cacheDirPath } = getCacheDirPath({
|
55
|
+
reactAppRootDirPath
|
48
56
|
});
|
49
57
|
|
50
|
-
if (!fs.existsSync(
|
51
|
-
fs.mkdirSync(
|
58
|
+
if (!fs.existsSync(cacheDirPath)) {
|
59
|
+
fs.mkdirSync(cacheDirPath, { "recursive": true });
|
52
60
|
}
|
53
61
|
|
54
62
|
fs.writeFileSync(
|
55
|
-
pathJoin(
|
63
|
+
pathJoin(cacheDirPath, resolvedViteConfigJsonBasename),
|
56
64
|
Buffer.from(
|
57
65
|
JSON.stringify(
|
58
66
|
id<ResolvedViteConfig>({
|
@@ -67,8 +75,18 @@ export function keycloakify(): Plugin {
|
|
67
75
|
"utf8"
|
68
76
|
)
|
69
77
|
);
|
78
|
+
|
79
|
+
await copyKeycloakResourcesToPublic({
|
80
|
+
"processArgv": ["--project", reactAppRootDirPath]
|
81
|
+
});
|
70
82
|
},
|
71
83
|
"transform": (code, id) => {
|
84
|
+
assert(command !== undefined);
|
85
|
+
|
86
|
+
if (command !== "build") {
|
87
|
+
return;
|
88
|
+
}
|
89
|
+
|
72
90
|
assert(reactAppRootDirPath !== undefined);
|
73
91
|
|
74
92
|
let transformedCode: string | undefined = undefined;
|
@@ -82,9 +100,8 @@ export function keycloakify(): Plugin {
|
|
82
100
|
}
|
83
101
|
}
|
84
102
|
|
85
|
-
const isJavascriptFile = id.endsWith(".js") || id.endsWith(".jsx");
|
86
|
-
|
87
103
|
{
|
104
|
+
const isJavascriptFile = id.endsWith(".js") || id.endsWith(".jsx");
|
88
105
|
const isTypeScriptFile = id.endsWith(".ts") || id.endsWith(".tsx");
|
89
106
|
|
90
107
|
if (!isTypeScriptFile && !isJavascriptFile) {
|
@@ -92,8 +109,6 @@ export function keycloakify(): Plugin {
|
|
92
109
|
}
|
93
110
|
}
|
94
111
|
|
95
|
-
const windowToken = isJavascriptFile ? "window" : "(window as any)";
|
96
|
-
|
97
112
|
if (transformedCode === undefined) {
|
98
113
|
transformedCode = code;
|
99
114
|
}
|
@@ -103,9 +118,9 @@ export function keycloakify(): Plugin {
|
|
103
118
|
"import.meta.env.BASE_URL",
|
104
119
|
[
|
105
120
|
`(`,
|
106
|
-
`(
|
107
|
-
`
|
108
|
-
`
|
121
|
+
`(window.${nameOfTheGlobal} === undefined || import.meta.env.MODE === "development")?`,
|
122
|
+
`"${urlPathname ?? "/"}":`,
|
123
|
+
`(window.${nameOfTheGlobal}.url.resourcesPath + "/${basenameOfTheKeycloakifyResourcesDir}/")`,
|
109
124
|
`)`
|
110
125
|
].join("")
|
111
126
|
);
|
@@ -119,10 +134,18 @@ export function keycloakify(): Plugin {
|
|
119
134
|
"code": transformedCode
|
120
135
|
};
|
121
136
|
},
|
122
|
-
"
|
137
|
+
"closeBundle": async () => {
|
138
|
+
assert(command !== undefined);
|
139
|
+
|
140
|
+
if (command !== "build") {
|
141
|
+
return;
|
142
|
+
}
|
143
|
+
|
123
144
|
assert(buildDirPath !== undefined);
|
124
145
|
|
125
146
|
await rm(pathJoin(buildDirPath, keycloak_resources), { "recursive": true, "force": true });
|
126
147
|
}
|
127
|
-
};
|
148
|
+
} satisfies Plugin;
|
149
|
+
|
150
|
+
return plugin as any;
|
128
151
|
}
|