From ff43970e9ab3ed72da3c7c25854b6fe1851702b2 Mon Sep 17 00:00:00 2001 From: mfrances17 <39063664+mfrances17@users.noreply.github.com> Date: Tue, 8 Dec 2020 01:30:53 -0500 Subject: [PATCH] User Federation: populate Kerberos required and cache settings data (#243) * pull in kerberos data * fix build fails and cleanup msgs * fix 2x build errs * fix broken test * fix route, bcrumb, and card click * lint fixes * final changes from PR review * add old breadcrumb functionality back * fix breadcrumb test * lint fix --- src/client-scopes/form/ClientScopeForm.tsx | 2 +- src/client-scopes/messages.json | 3 - src/clients/ClientDetails.tsx | 2 +- src/clients/messages.json | 1 - src/common-messages.json | 2 + src/components/keycloak-card/KeycloakCard.tsx | 16 +++- src/route-config.ts | 7 ++ src/user-federation/KerberosSettingsCache.tsx | 77 ++++++++++++++----- .../KerberosSettingsRequired.tsx | 50 ++++++++---- 9 files changed, 122 insertions(+), 38 deletions(-) diff --git a/src/client-scopes/form/ClientScopeForm.tsx b/src/client-scopes/form/ClientScopeForm.tsx index 5c2a295d8e..630d730566 100644 --- a/src/client-scopes/form/ClientScopeForm.tsx +++ b/src/client-scopes/form/ClientScopeForm.tsx @@ -103,7 +103,7 @@ export const ClientScopeForm = () => { > {t("settings")}} + title={{t("common:settings")}} >
{ > {t("settings")}} + title={{t("common:settings")}} > diff --git a/src/clients/messages.json b/src/clients/messages.json index a63647b402..b55d975dd6 100644 --- a/src/clients/messages.json +++ b/src/clients/messages.json @@ -11,7 +11,6 @@ "name": "Name", "formatOption": "Format option", "downloadAdaptorTitle": "Download adaptor configs", - "settings": "Settings", "credentials": "Credentials", "clientScopes": "Client scopes", "addClientScope": "Add client scope", diff --git a/src/common-messages.json b/src/common-messages.json index 41eaa73aee..682e3b0e07 100644 --- a/src/common-messages.json +++ b/src/common-messages.json @@ -52,6 +52,8 @@ "identityProviders": "Identity providers", "userFederation": "User federation", + "settings": "Settings", + "required": "Required field", "maxLength": "Max length {{length}}", diff --git a/src/components/keycloak-card/KeycloakCard.tsx b/src/components/keycloak-card/KeycloakCard.tsx index 08f0fafd13..abc79f5aca 100644 --- a/src/components/keycloak-card/KeycloakCard.tsx +++ b/src/components/keycloak-card/KeycloakCard.tsx @@ -13,6 +13,7 @@ import { FlexItem, } from "@patternfly/react-core"; import "./keycloak-card.css"; +import { useHistory } from "react-router-dom"; export type KeycloakCardProps = { id: string; @@ -26,6 +27,7 @@ export type KeycloakCardProps = { }; export const KeycloakCard = ({ + id, dropdownItems, title, labelText, @@ -33,12 +35,23 @@ export const KeycloakCard = ({ footerText, }: KeycloakCardProps) => { const [isDropdownOpen, setIsDropdownOpen] = useState(false); + + const history = useHistory(); + const onDropdownToggle = () => { setIsDropdownOpen(!isDropdownOpen); }; + const handleCardMenuClick = (e: any) => { + e.stopPropagation(); + }; + + const openSettings = () => { + history.push(`/user-federation/${id}`); + }; + return ( - + {dropdownItems && ( @@ -46,6 +59,7 @@ export const KeycloakCard = ({ isPlain position={"right"} toggle={} + onClick={(e) => handleCardMenuClick(e)} isOpen={isDropdownOpen} dropdownItems={dropdownItems} /> diff --git a/src/route-config.ts b/src/route-config.ts index 6df8c63fa7..d4c2f52010 100644 --- a/src/route-config.ts +++ b/src/route-config.ts @@ -20,6 +20,7 @@ import { UserFederationSection } from "./user-federation/UserFederationSection"; import { UsersSection } from "./user/UsersSection"; import { MappingDetails } from "./client-scopes/details/MappingDetails"; import { ClientDetails } from "./clients/ClientDetails"; +import { UserFederationKerberosSettings } from "./user-federation/UserFederationKerberosSettings"; import { RoleMappingForm } from "./client-scopes/add/RoleMappingForm"; export type RouteDef = { @@ -164,6 +165,12 @@ export const routes: RoutesFn = (t: TFunction) => [ breadcrumb: t("userFederation"), access: "view-realm", }, + { + path: "/user-federation/:id", + component: UserFederationKerberosSettings, + breadcrumb: t("common:settings"), + access: "view-realm", + }, { path: "/", component: ClientsSection, diff --git a/src/user-federation/KerberosSettingsCache.tsx b/src/user-federation/KerberosSettingsCache.tsx index d844b3ba5d..3867f56b42 100644 --- a/src/user-federation/KerberosSettingsCache.tsx +++ b/src/user-federation/KerberosSettingsCache.tsx @@ -7,15 +7,63 @@ import { } from "@patternfly/react-core"; import { useTranslation } from "react-i18next"; import { HelpItem } from "../components/help-enabler/HelpItem"; -import React, { useState } from "react"; +import React, { useEffect, useState } from "react"; import { useForm, Controller } from "react-hook-form"; +import { convertToFormValues } from "../util"; import ComponentRepresentation from "keycloak-admin/lib/defs/componentRepresentation"; import { FormAccess } from "../components/form-access/FormAccess"; +import { useAdminClient } from "../context/auth/AdminClient"; +import { useParams } from "react-router-dom"; export const KerberosSettingsCache = () => { const { t } = useTranslation("user-federation"); const helpText = useTranslation("user-federation-help").t; + const adminClient = useAdminClient(); + const { register, control, setValue } = useForm(); + const { id } = useParams<{ id: string }>(); + + const convertToDays = (num: string) => { + switch (num) { + case "1": + return t("common:Sunday"); + case "2": + return t("common:Monday"); + case "3": + return t("common:Tuesday"); + case "4": + return t("common:Wednesday"); + case "5": + return t("common:Thursday"); + case "6": + return t("common:Friday"); + case "7": + return t("common:Saturday"); + default: + return t("common:selectOne"); + } + }; + + const setupForm = (component: ComponentRepresentation) => { + Object.entries(component).map((entry) => { + if (entry[0] === "config") { + convertToFormValues(entry[1], "config", setValue); + setValue("config.evictionDay", convertToDays(entry[1].evictionDay[0])); + } else { + setValue(entry[0], entry[1]); + } + }); + }; + + useEffect(() => { + (async () => { + const fetchedComponent = await adminClient.components.findOne({ id }); + if (fetchedComponent) { + setupForm(fetchedComponent); + } + })(); + }, []); + const [isCachePolicyDropdownOpen, setIsCachePolicyDropdownOpen] = useState( false ); @@ -30,8 +78,6 @@ export const KerberosSettingsCache = () => { false ); - const { control, register } = useForm(); - const hourOptions = [ , ]; @@ -62,7 +108,7 @@ export const KerberosSettingsCache = () => { fieldId="kc-cache-policy" > ( @@ -85,14 +131,15 @@ export const KerberosSettingsCache = () => { value={t("common:selectOne")} isPlaceholder /> - - + + + + + )} > - - {/* TODO: Field shows only if cache policy is EVICT_WEEKLY */} { fieldId="kc-eviction-day" > ( @@ -139,8 +186,6 @@ export const KerberosSettingsCache = () => { )} > - - {/* TODO: Field shows only if cache policy is EVICT_WEEKLY or EVICT_DAILY */} {/* TODO: Investigate whether this should be a number field instead of a dropdown/text field */} { fieldId="kc-eviction-hour" > ( @@ -176,8 +221,6 @@ export const KerberosSettingsCache = () => { )} > - - {/* TODO: Field shows only if cache policy is EVICT_WEEKLY or EVICT_DAILY */} {/* TODO: Investigate whether this should be a number field instead of a dropdown/text field */} { fieldId="kc-eviction-minute" > ( @@ -213,8 +256,6 @@ export const KerberosSettingsCache = () => { )} > - - {/* TODO: Field shows only if cache policy is MAX_LIFESPAN */} { isRequired type="text" id="kc-max-lifespan" - name="maxLifespan" + name="config.maxLifespan" ref={register} /> diff --git a/src/user-federation/KerberosSettingsRequired.tsx b/src/user-federation/KerberosSettingsRequired.tsx index 5d973c034d..ceb1fb2cc6 100644 --- a/src/user-federation/KerberosSettingsRequired.tsx +++ b/src/user-federation/KerberosSettingsRequired.tsx @@ -1,3 +1,4 @@ +import React, { useEffect, useState } from "react"; import { FormGroup, Select, @@ -8,17 +9,39 @@ import { } from "@patternfly/react-core"; import { useTranslation } from "react-i18next"; import { HelpItem } from "../components/help-enabler/HelpItem"; -import React, { useState } from "react"; import { useForm, Controller } from "react-hook-form"; import ComponentRepresentation from "keycloak-admin/lib/defs/componentRepresentation"; import { FormAccess } from "../components/form-access/FormAccess"; +import { useAdminClient } from "../context/auth/AdminClient"; +import { useParams } from "react-router-dom"; +import { convertToFormValues } from "../util"; export const KerberosSettingsRequired = () => { const { t } = useTranslation("user-federation"); const helpText = useTranslation("user-federation-help").t; - + const adminClient = useAdminClient(); const [isEditModeDropdownOpen, setIsEditModeDropdownOpen] = useState(false); - const { register, control } = useForm(); + const { register, control, setValue } = useForm(); + const { id } = useParams<{ id: string }>(); + + const setupForm = (component: ComponentRepresentation) => { + Object.entries(component).map((entry) => { + if (entry[0] === "config") { + convertToFormValues(entry[1], "config", setValue); + } else { + setValue(entry[0], entry[1]); + } + }); + }; + + useEffect(() => { + (async () => { + const fetchedComponent = await adminClient.components.findOne({ id }); + if (fetchedComponent) { + setupForm(fetchedComponent); + } + })(); + }, []); return ( <> @@ -40,7 +63,7 @@ export const KerberosSettingsRequired = () => { isRequired type="text" id="kc-console-display-name" - name="consoleDisplayName" + name="name" ref={register} /> @@ -61,7 +84,7 @@ export const KerberosSettingsRequired = () => { isRequired type="text" id="kc-kerberos-realm" - name="kerberosRealm" + name="config.kerberosRealm" ref={register} /> @@ -82,7 +105,7 @@ export const KerberosSettingsRequired = () => { isRequired type="text" id="kc-server-principal" - name="serverPrincipal" + name="config.serverPrincipal" ref={register} /> @@ -103,7 +126,7 @@ export const KerberosSettingsRequired = () => { isRequired type="text" id="kc-key-tab" - name="keyTab" + name="config.keyTab" ref={register} /> @@ -122,7 +145,7 @@ export const KerberosSettingsRequired = () => { > {" "} ( @@ -151,7 +174,7 @@ export const KerberosSettingsRequired = () => { hasNoPaddingTop > ( @@ -181,8 +204,8 @@ export const KerberosSettingsRequired = () => { > {" "} ( )} > @@ -223,7 +247,7 @@ export const KerberosSettingsRequired = () => { hasNoPaddingTop > (