commit
853fd2c220
21 changed files with 530 additions and 28 deletions
|
@ -16,6 +16,8 @@
|
|||
"search": "Search",
|
||||
"next": "Next",
|
||||
"back": "Back",
|
||||
"finish": "Finish",
|
||||
"skipCustomizationAndFinish": "Skip customization and finish",
|
||||
"export": "Export",
|
||||
"action": "Action",
|
||||
"download": "Download",
|
||||
|
@ -36,6 +38,7 @@
|
|||
"documentation": "Documentation",
|
||||
"enableHelpMode": "Enable help mode",
|
||||
"learnMore": "Learn more",
|
||||
"test": "Test",
|
||||
|
||||
"home": "Home",
|
||||
"manage": "Manage",
|
||||
|
|
|
@ -44,7 +44,7 @@ export const ScrollForm = ({ sections, children }: ScrollFormProps) => {
|
|||
// to scroll the entire main section, it has to be the pf-c-page__main
|
||||
scrollableSelector={mainPageContentId}
|
||||
label={t("jumpToSection")}
|
||||
offset={76}
|
||||
offset={100}
|
||||
>
|
||||
{sections.map((cat) => (
|
||||
// note that JumpLinks currently does not work with spaces in the href
|
||||
|
|
53
src/components/wizard-section-header/WizardSectionHeader.tsx
Normal file
53
src/components/wizard-section-header/WizardSectionHeader.tsx
Normal file
|
@ -0,0 +1,53 @@
|
|||
import React, { ReactElement, useContext, useState } from "react";
|
||||
import {
|
||||
Text,
|
||||
PageSection,
|
||||
TextContent,
|
||||
Divider,
|
||||
Level,
|
||||
LevelItem,
|
||||
Switch,
|
||||
Toolbar,
|
||||
ToolbarContent,
|
||||
ToolbarItem,
|
||||
Badge,
|
||||
ButtonProps,
|
||||
Dropdown,
|
||||
DropdownToggle,
|
||||
DropdownPosition,
|
||||
Title,
|
||||
} from "@patternfly/react-core";
|
||||
import "./wizard-section-header.css";
|
||||
|
||||
export type WizardSectionHeaderProps = {
|
||||
title: string;
|
||||
description?: string;
|
||||
showDescription?: boolean;
|
||||
};
|
||||
|
||||
export const WizardSectionHeader = ({
|
||||
title,
|
||||
description,
|
||||
showDescription = false,
|
||||
}: WizardSectionHeaderProps) => {
|
||||
return (
|
||||
<>
|
||||
<Title
|
||||
size={"xl"}
|
||||
headingLevel={"h2"}
|
||||
className={
|
||||
showDescription
|
||||
? "kc-wizard-section-header__title--has-description"
|
||||
: "kc-wizard-section-header__title"
|
||||
}
|
||||
>
|
||||
{title}
|
||||
</Title>
|
||||
{showDescription && (
|
||||
<TextContent className="kc-wizard-section-header__description">
|
||||
<Text>{description}</Text>
|
||||
</TextContent>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
};
|
|
@ -0,0 +1,10 @@
|
|||
.kc-wizard-section-header__title {
|
||||
margin-bottom: var(--pf-global--spacer--lg);
|
||||
}
|
||||
.kc-wizard-section-header__title--has-description {
|
||||
margin-bottom: var(--pf-global--spacer--sm);
|
||||
}
|
||||
|
||||
.kc-wizard-section-header__description {
|
||||
margin-bottom: var(--pf-global--spacer--lg);
|
||||
}
|
22
src/stories/UserFedKerberosWizard.stories.tsx
Normal file
22
src/stories/UserFedKerberosWizard.stories.tsx
Normal file
|
@ -0,0 +1,22 @@
|
|||
import React from "react";
|
||||
import { Meta } from "@storybook/react";
|
||||
import { Page, PageSection } from "@patternfly/react-core";
|
||||
import { UserFederationKerberosWizard } from "../user-federation/UserFederationKerberosWizard";
|
||||
import { MockAdminClient } from "./MockAdminClient";
|
||||
|
||||
export default {
|
||||
title: "User Federation Kerberos Wizard",
|
||||
component: UserFederationKerberosWizard,
|
||||
} as Meta;
|
||||
|
||||
export const view = () => {
|
||||
return (
|
||||
<Page style={{ height: "80vh" }}>
|
||||
<PageSection isFilled>
|
||||
<MockAdminClient>
|
||||
<UserFederationKerberosWizard />
|
||||
</MockAdminClient>
|
||||
</PageSection>
|
||||
</Page>
|
||||
);
|
||||
};
|
20
src/stories/UserFedLdapWizard.stories.tsx
Normal file
20
src/stories/UserFedLdapWizard.stories.tsx
Normal file
|
@ -0,0 +1,20 @@
|
|||
import React from "react";
|
||||
import { Meta } from "@storybook/react";
|
||||
import { Page } from "@patternfly/react-core";
|
||||
import { UserFederationLdapWizard } from "../user-federation/UserFederationLdapWizard";
|
||||
import { MockAdminClient } from "./MockAdminClient";
|
||||
|
||||
export default {
|
||||
title: "User Federation LDAP Wizard",
|
||||
component: UserFederationLdapWizard,
|
||||
} as Meta;
|
||||
|
||||
export const view = () => {
|
||||
return (
|
||||
<Page style={{ height: "80vh" }}>
|
||||
<MockAdminClient>
|
||||
<UserFederationLdapWizard />
|
||||
</MockAdminClient>{" "}
|
||||
</Page>
|
||||
);
|
||||
};
|
22
src/stories/WizardSectionHeader.stories.tsx
Normal file
22
src/stories/WizardSectionHeader.stories.tsx
Normal file
|
@ -0,0 +1,22 @@
|
|||
import React from "react";
|
||||
import { Meta, Story } from "@storybook/react";
|
||||
import {
|
||||
WizardSectionHeader,
|
||||
WizardSectionHeaderProps,
|
||||
} from "../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export default {
|
||||
title: "Wizard Section Header",
|
||||
component: WizardSectionHeader,
|
||||
} as Meta;
|
||||
|
||||
const Template: Story<WizardSectionHeaderProps> = (args) => (
|
||||
<WizardSectionHeader {...args} />
|
||||
);
|
||||
|
||||
export const TitleAndDescription = Template.bind({});
|
||||
TitleAndDescription.args = {
|
||||
title: "Section title",
|
||||
description: "This is a description of the section",
|
||||
showDescription: true,
|
||||
};
|
|
@ -1,27 +1,16 @@
|
|||
import { PageSection, Title } from "@patternfly/react-core";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import { PageSection } from "@patternfly/react-core";
|
||||
import React from "react";
|
||||
import { KerberosSettingsRequired } from "./kerberos/KerberosSettingsRequired";
|
||||
import { KerberosSettingsCache } from "./kerberos/KerberosSettingsCache";
|
||||
|
||||
export const UserFederationKerberosSettings = () => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
|
||||
return (
|
||||
<>
|
||||
<PageSection variant="light">
|
||||
{/* Required settings */}
|
||||
<Title size={"xl"} headingLevel={"h2"} className="pf-u-mb-lg">
|
||||
{t("requiredSettings")}
|
||||
</Title>
|
||||
<KerberosSettingsRequired />
|
||||
<KerberosSettingsRequired showSectionHeading />
|
||||
</PageSection>
|
||||
<PageSection variant="light" isFilled>
|
||||
{/* Cache settings */}
|
||||
<Title size={"xl"} headingLevel={"h2"} className="pf-u-mb-lg">
|
||||
{t("cacheSettings")}
|
||||
</Title>
|
||||
<KerberosSettingsCache />
|
||||
<KerberosSettingsCache showSectionHeading />
|
||||
</PageSection>
|
||||
</>
|
||||
);
|
||||
|
|
34
src/user-federation/UserFederationKerberosWizard.tsx
Normal file
34
src/user-federation/UserFederationKerberosWizard.tsx
Normal file
|
@ -0,0 +1,34 @@
|
|||
import { Wizard } from "@patternfly/react-core";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import React from "react";
|
||||
import { KerberosSettingsRequired } from "./kerberos/KerberosSettingsRequired";
|
||||
import { KerberosSettingsCache } from "./kerberos/KerberosSettingsCache";
|
||||
|
||||
export const UserFederationKerberosWizard = () => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
|
||||
const steps = [
|
||||
{
|
||||
name: t("requiredSettings"),
|
||||
component: (
|
||||
<KerberosSettingsRequired showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("cacheSettings"),
|
||||
component: (
|
||||
<KerberosSettingsCache showSectionHeading showSectionDescription />
|
||||
),
|
||||
nextButtonText: t("common:finish"), // TODO: needs to disable until cache policy is valid
|
||||
},
|
||||
];
|
||||
|
||||
return (
|
||||
<Wizard
|
||||
// Because this is an inline wizard, this title and description should be put into the page. Specifying them here causes the wizard component to make a header that would be used on a modal.
|
||||
// title={t("addKerberosWizardTitle")}
|
||||
// description={helpText("addKerberosWizardDescription")}
|
||||
steps={steps}
|
||||
/>
|
||||
);
|
||||
};
|
172
src/user-federation/UserFederationLdapWizard.tsx
Normal file
172
src/user-federation/UserFederationLdapWizard.tsx
Normal file
|
@ -0,0 +1,172 @@
|
|||
import {
|
||||
Button,
|
||||
Wizard,
|
||||
WizardContextConsumer,
|
||||
WizardFooter,
|
||||
} from "@patternfly/react-core";
|
||||
import React from "react";
|
||||
import { LdapSettingsGeneral } from "./ldap/LdapSettingsGeneral";
|
||||
import { LdapSettingsConnection } from "./ldap/LdapSettingsConnection";
|
||||
import { LdapSettingsSearching } from "./ldap/LdapSettingsSearching";
|
||||
import { LdapSettingsSynchronization } from "./ldap/LdapSettingsSynchronization";
|
||||
import { LdapSettingsKerberosIntegration } from "./ldap/LdapSettingsKerberosIntegration";
|
||||
import { LdapSettingsCache } from "./ldap/LdapSettingsCache";
|
||||
import { LdapSettingsAdvanced } from "./ldap/LdapSettingsAdvanced";
|
||||
import { useTranslation } from "react-i18next";
|
||||
|
||||
export const UserFederationLdapWizard = () => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
|
||||
const steps = [
|
||||
{
|
||||
name: t("requiredSettings"),
|
||||
id: "ldapRequiredSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsGeneral showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("connectionAndAuthenticationSettings"),
|
||||
id: "ldapConnectionSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsConnection showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("ldapSearchingAndUpdatingSettings"),
|
||||
id: "ldapSearchingSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsSearching showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("synchronizationSettings"),
|
||||
id: "ldapSynchronizationSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsSynchronization
|
||||
showSectionHeading
|
||||
showSectionDescription
|
||||
/>
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("kerberosIntegration"),
|
||||
id: "ldapKerberosIntegrationSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsKerberosIntegration
|
||||
showSectionHeading
|
||||
showSectionDescription
|
||||
/>
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("cacheSettings"),
|
||||
id: "ldapCacheSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsCache showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
{
|
||||
name: t("advancedSettings"),
|
||||
id: "ldapAdvancedSettingsStep",
|
||||
component: (
|
||||
<LdapSettingsAdvanced showSectionHeading showSectionDescription />
|
||||
),
|
||||
},
|
||||
];
|
||||
|
||||
const footer = (
|
||||
<WizardFooter>
|
||||
<WizardContextConsumer>
|
||||
{({ activeStep, onNext, onBack, onClose }) => {
|
||||
// First step buttons
|
||||
if (activeStep.id == "ldapRequiredSettingsStep") {
|
||||
return (
|
||||
<>
|
||||
<Button variant="primary" type="submit" onClick={onNext}>
|
||||
{t("common:next")}
|
||||
</Button>
|
||||
<Button
|
||||
variant="secondary"
|
||||
onClick={onBack}
|
||||
className="pf-m-disabled"
|
||||
>
|
||||
{t("common:back")}
|
||||
</Button>
|
||||
<Button variant="link" onClick={onClose}>
|
||||
{t("common:cancel")}
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
}
|
||||
// Other required step buttons
|
||||
else if (
|
||||
activeStep.id == "ldapConnectionSettingsStep" ||
|
||||
activeStep.id == "ldapSearchingSettingsStep"
|
||||
) {
|
||||
return (
|
||||
<>
|
||||
<Button variant="primary" type="submit" onClick={onNext}>
|
||||
{t("common:next")}
|
||||
</Button>
|
||||
<Button variant="secondary" onClick={onBack}>
|
||||
{t("common:back")}
|
||||
</Button>
|
||||
<Button variant="link" onClick={onClose}>
|
||||
{t("common:cancel")}
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
}
|
||||
// Last step buttons
|
||||
else if (activeStep.id == "ldapAdvancedSettingsStep") {
|
||||
return (
|
||||
<>
|
||||
<Button
|
||||
onClick={() => {}} //TODO: close the wizard and finish
|
||||
>
|
||||
{t("common:finish")}
|
||||
</Button>
|
||||
<Button variant="secondary" onClick={onBack}>
|
||||
{t("common:back")}
|
||||
</Button>
|
||||
<Button variant="link" onClick={onClose}>
|
||||
{t("common:cancel")}
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
}
|
||||
// All the other steps buttons
|
||||
return (
|
||||
<>
|
||||
<Button onClick={onNext}>Next</Button>
|
||||
<Button variant="secondary" onClick={onBack}>
|
||||
Back
|
||||
</Button>
|
||||
<Button
|
||||
variant="link"
|
||||
onClick={() => {}} //TODO: validate last step and finish
|
||||
>
|
||||
{t("common:skipCustomizationAndFinish")}
|
||||
</Button>
|
||||
<Button variant="link" onClick={onClose}>
|
||||
{t("common:cancel")}
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
}}
|
||||
</WizardContextConsumer>
|
||||
</WizardFooter>
|
||||
);
|
||||
|
||||
return (
|
||||
<Wizard
|
||||
// Because this is an inline wizard, this title and description should be put into the page. Specifying them here causes the wizard component to make a header that would be used on a modal.
|
||||
// title={t("addLdapWizardTitle")}
|
||||
// description={helpText("addLdapWizardDescription")}
|
||||
height="100%"
|
||||
steps={steps}
|
||||
footer={footer}
|
||||
/>
|
||||
);
|
||||
};
|
|
@ -1,9 +1,13 @@
|
|||
{
|
||||
"user-federation-help": {
|
||||
"generalOptions": "General options",
|
||||
"addKerberosWizardDescription": "Text needed here",
|
||||
"addLdapWizardDescription": "Text needed here",
|
||||
|
||||
"ldapGeneralOptionsSettingsDescription": "This section contains a few basic options common to all user storage providers.",
|
||||
"consoleDisplayNameHelp": "Display name of provider when linked in admin console",
|
||||
"vendorHelp": "LDAP vendor (provider)",
|
||||
|
||||
"ldapConnectionAndAuthorizationSettingsDescription": "This section contains options related to the configuration of the connection to the LDAP server. It also contains options related to authentication of the LDAP connection to the LDAP server.",
|
||||
"consoleDisplayConnectionUrlHelp": "Connection URL to your LDAP server",
|
||||
"enableStarttlsHelp": "Encrypts the connection to LDAP using STARTTLS, which will disable connection pooling",
|
||||
"useTruststoreSpiHelp": "Specifies whether LDAP connection will use the Truststore SPI with the truststore configured in standalone.xml/domain.sml. 'Always' means that it will always use it. 'Never' means that it will not use it. 'Only for ldaps' means that it will use it if your connection URL use ldaps. Note even if standalone.xml/domain.xml is not configured, the default java cacerts or certificate specified by 'javax.net.ssl.trustStore' property will be used.",
|
||||
|
@ -13,6 +17,7 @@
|
|||
"bindDnHelp": "DN of the LDAP admin, which will be used by Keycloak to access LDAP server",
|
||||
"bindCredentialsHelp": "Password of LDAP admin. This field is able to obtain its value from vault, use ${vault.ID} format.",
|
||||
|
||||
"ldapSearchingAndUpdatingSettingsDescription": "This section contains options related to searching the LDAP server for the available users.",
|
||||
"editModeLdapHelp": "READ_ONLY is a read-only LDAP store. WRITABLE means data will be synced back to LDAP on demand. UNSYNCED means user data will be imported, but not synced back to LDAP.",
|
||||
"usersDNHelp": "Full DN of LDAP tree where your users are. This DN is the parent of LDAP users. It could be for example 'ou=users,dc=example,dc=com' assuming that your typical user will have DN like 'uid='john',ou=users,dc=example,dc=com'",
|
||||
"usernameLdapAttributeHelp": "Name of LDAP attribute, which is mapped as Keycloak username. For many LDAP server vendors it can be 'uid'. For Active directory it can be 'sAMAccountName' or 'cn'. The attribute should be filled for all LDAP user records you want to import from LDAP to Keycloak.",
|
||||
|
@ -24,33 +29,41 @@
|
|||
"readTimeoutHelp": "LDAP read timeout in milliseconds. This timeout applies for LDAP read operations.",
|
||||
"paginationHelp": "Does the LDAP server support pagination",
|
||||
|
||||
"ldapSynchronizationSettingsDescription": "This section contains options related to synchronization of users from LDAP to the Keycloak database.",
|
||||
"importUsersHelp": "Import users",
|
||||
"batchSizeHelp": "Count of LDAP users to be imported from LDAP to Keycloak within a single transaction",
|
||||
"periodicFullSyncHelp": "Whether periodic full synchronization of LDAP users to Keycloak should be enabled or not",
|
||||
"periodicChangedUsersSyncHelp": "Whether periodic synchronization of changed or newly created LDAP users to Keycloak should be enabled or not",
|
||||
|
||||
"ldapKerberosSettingsDescription": "This section contains options useful for the Kerberos integraion. This is used just when the LDAP server is used together with Kerberos/SPNEGO for user authentication.",
|
||||
"allowKerberosAuthenticationHelp": "Enable/disable HTTP authentication of users with SPNEGO/Kerberos tokens. The data about authenticated users will be provisioned from this LDAP server",
|
||||
"useKerberosForPasswordAuthenticationHelp": "User Kerberos login module for authenticate username/password against Kerberos server instead of authenticating against LDAP server with Directory Service API",
|
||||
|
||||
"ldapCacheSettingsDescription": "This section contains options useful for caching users, which were loaded from this user storage provider",
|
||||
"cachePolicyHelp": "Cache Policy for this storage provider. 'DEFAULT' is whatever the default settings are for the global cache. 'EVICT_DAILY' is a time of day every day that the cache will be invalidated. 'EVICT_WEEKLY' is a day of the week and time the cache will be invalidated. 'MAX_LIFESPAN' is the time in milliseconds that will be the lifespan of a cache entry.",
|
||||
"evictionDayHelp": "Day of the week the entry will become invalid",
|
||||
"evictionHourHelp": "Hour of the day the entry will become invalid",
|
||||
"evictionMinuteHelp": "Minute of the hour the entry will become invalid",
|
||||
"maxLifespanHelp": "Max lifespan of cache entry in milliseconds",
|
||||
|
||||
"ldapAdvancedSettingsDescription": "This section contains all the other options for more fine-grained configuration of the LDAP storage provider.",
|
||||
"enableLdapv3PasswordHelp": "Use the LDAPv3 Password Modify Extended Operation (RFC-3062). The password modify extended operation usually requires that LDAP user already has password in the LDAP server. So when this is used with 'Sync Registrations', it can be good to add also 'Hardcoded LDAP attribute mapper' with randomly generated initial password.",
|
||||
"validatePasswordPolicyHelp": "Determines if Keycloak should validate the password with the realm password policy before updating it",
|
||||
"trustEmailHelp": "If enabled, email provided by this provider is not verified even if verification is enabled for the realm.",
|
||||
|
||||
"IDK-periodicChangedUsersSyncHelp": "Should newly created users be created within LDAP store? Priority affects which provider is chosen to sync the new user.",
|
||||
|
||||
"requiredSettingsHelp": "Required Settings",
|
||||
"kerberosWizardDescription": "Text needed here",
|
||||
|
||||
"kerberosRequiredSettingsDescription": "This section contains a few basic options common to all user storage providers.",
|
||||
"kerberosRealmHelp": "Name of kerberos realm. For example, FOO.ORG",
|
||||
"serverPrincipalHelp": "Full name of server principal for HTTP service including server and domain name. For example, HTTP/host.foo.org@FOO.ORG",
|
||||
"keyTabHelp": "Location of Kerberos KeyTab file containing the credentials of server principal. For example, /etc/krb5.keytab",
|
||||
"debugHelp": "Enable/disable debug logging to standard output for Krb5LoginModule",
|
||||
"allowPasswordAuthenticationHelp": "Enable/disable possibility of username/password authentication against Kerberos database",
|
||||
"editModeKerberosHelp": "READ_ONLY means that password updates are not allowed and user always authenticates with Kerberos password. UNSYNCED means that the user can change the password in the Keycloak database and this one will be used instead of the Kerberos password",
|
||||
"updateFirstLoginHelp": "Update profile on first login"
|
||||
"updateFirstLoginHelp": "Update profile on first login",
|
||||
|
||||
"kerberosCacheSettingsDescription": "This section contains a few basic options common to all user storage providers"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,8 +18,17 @@ import {
|
|||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import _ from "lodash";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const KerberosSettingsCache = () => {
|
||||
export type KerberosSettingsCacheProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const KerberosSettingsCache = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: KerberosSettingsCacheProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
|
||||
|
@ -80,6 +89,14 @@ export const KerberosSettingsCache = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("cacheSettings")}
|
||||
description={helpText("kerberosCacheSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Cache settings */}
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
|
|
|
@ -6,6 +6,7 @@ import {
|
|||
SelectVariant,
|
||||
Switch,
|
||||
TextInput,
|
||||
Title,
|
||||
} from "@patternfly/react-core";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import { HelpItem } from "../../components/help-enabler/HelpItem";
|
||||
|
@ -16,8 +17,17 @@ import { useAdminClient } from "../../context/auth/AdminClient";
|
|||
import { useParams } from "react-router-dom";
|
||||
import { convertToFormValues } from "../../util";
|
||||
import _ from "lodash";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const KerberosSettingsRequired = () => {
|
||||
export type KerberosSettingsRequiredProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const KerberosSettingsRequired = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: KerberosSettingsRequiredProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
const adminClient = useAdminClient();
|
||||
|
@ -54,6 +64,14 @@ export const KerberosSettingsRequired = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("requiredSettings")}
|
||||
description={helpText("kerberosRequiredSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Required settings */}
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
|
|
|
@ -11,8 +11,17 @@ import {
|
|||
asyncStateFetch,
|
||||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsAdvanced = () => {
|
||||
export type LdapSettingsAdvancedProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsAdvanced = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsAdvancedProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
const adminClient = useAdminClient();
|
||||
|
@ -38,6 +47,14 @@ export const LdapSettingsAdvanced = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("advancedSettings")}
|
||||
description={helpText("ldapAdvancedSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
label={t("enableLdapv3Password")}
|
||||
|
|
|
@ -3,7 +3,10 @@ import {
|
|||
Select,
|
||||
SelectOption,
|
||||
SelectVariant,
|
||||
Text,
|
||||
TextContent,
|
||||
TextInput,
|
||||
Title,
|
||||
} from "@patternfly/react-core";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import React, { useEffect, useState } from "react";
|
||||
|
@ -14,8 +17,17 @@ import ComponentRepresentation from "keycloak-admin/lib/defs/componentRepresenta
|
|||
import { FormAccess } from "../../components/form-access/FormAccess";
|
||||
import { useAdminClient } from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsCache = () => {
|
||||
export type LdapSettingsCacheProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsCache = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsCacheProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
|
||||
|
@ -102,6 +114,14 @@ export const LdapSettingsCache = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("cacheSettings")}
|
||||
description={helpText("ldapCacheSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Cache settings */}
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
|
|
|
@ -21,8 +21,17 @@ import {
|
|||
asyncStateFetch,
|
||||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsConnection = () => {
|
||||
export type LdapSettingsConnectionProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsConnection = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsConnectionProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
const adminClient = useAdminClient();
|
||||
|
@ -73,6 +82,16 @@ export const LdapSettingsConnection = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("connectionAndAuthenticationSettings")}
|
||||
description={helpText(
|
||||
"ldapConnectionAndAuthorizationSettingsDescription"
|
||||
)}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
label={t("connectionURL")}
|
||||
|
@ -293,7 +312,7 @@ export const LdapSettingsConnection = () => {
|
|||
{" "}
|
||||
{/* TODO: whatever this button is supposed to do */}
|
||||
<Button variant="secondary" id="kc-test-button">
|
||||
Test
|
||||
{t("common:test")}
|
||||
</Button>
|
||||
</FormGroup>
|
||||
</FormAccess>
|
||||
|
|
|
@ -3,7 +3,10 @@ import {
|
|||
Select,
|
||||
SelectOption,
|
||||
SelectVariant,
|
||||
Text,
|
||||
TextContent,
|
||||
TextInput,
|
||||
Title,
|
||||
} from "@patternfly/react-core";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import React, { useEffect, useState } from "react";
|
||||
|
@ -17,8 +20,17 @@ import {
|
|||
asyncStateFetch,
|
||||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsGeneral = () => {
|
||||
export type LdapSettingsGeneralProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsGeneral = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsGeneralProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
const adminClient = useAdminClient();
|
||||
|
@ -65,6 +77,14 @@ export const LdapSettingsGeneral = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("generalOptions")}
|
||||
description={helpText("ldapGeneralOptionsSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
label={t("consoleDisplayName")}
|
||||
|
|
|
@ -11,8 +11,17 @@ import {
|
|||
asyncStateFetch,
|
||||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsKerberosIntegration = () => {
|
||||
export type LdapSettingsKerberosIntegrationProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsKerberosIntegration = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsKerberosIntegrationProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
|
||||
|
@ -39,6 +48,14 @@ export const LdapSettingsKerberosIntegration = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("kerberosIntegration")}
|
||||
description={helpText("ldapKerberosSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
label={t("allowKerberosAuthentication")}
|
||||
|
|
|
@ -18,8 +18,17 @@ import {
|
|||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { convertToFormValues } from "../../util";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsSearching = () => {
|
||||
export type LdapSettingsSearchingProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsSearching = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsSearchingProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const adminClient = useAdminClient();
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
|
@ -65,6 +74,14 @@ export const LdapSettingsSearching = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("ldapSearchingAndUpdatingSettings")}
|
||||
description={helpText("ldapSearchingAndUpdatingSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
label={t("editMode")}
|
||||
|
|
|
@ -11,8 +11,17 @@ import {
|
|||
asyncStateFetch,
|
||||
} from "../../context/auth/AdminClient";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { WizardSectionHeader } from "../../components/wizard-section-header/WizardSectionHeader";
|
||||
|
||||
export const LdapSettingsSynchronization = () => {
|
||||
export type LdapSettingsSynchronizationProps = {
|
||||
showSectionHeading?: boolean;
|
||||
showSectionDescription?: boolean;
|
||||
};
|
||||
|
||||
export const LdapSettingsSynchronization = ({
|
||||
showSectionHeading = false,
|
||||
showSectionDescription = false,
|
||||
}: LdapSettingsSynchronizationProps) => {
|
||||
const { t } = useTranslation("user-federation");
|
||||
const helpText = useTranslation("user-federation-help").t;
|
||||
const adminClient = useAdminClient();
|
||||
|
@ -38,6 +47,14 @@ export const LdapSettingsSynchronization = () => {
|
|||
|
||||
return (
|
||||
<>
|
||||
{showSectionHeading && (
|
||||
<WizardSectionHeader
|
||||
title={t("synchronizationSettings")}
|
||||
description={helpText("ldapSynchronizationSettingsDescription")}
|
||||
showDescription={showSectionDescription}
|
||||
/>
|
||||
)}
|
||||
|
||||
<FormAccess role="manage-realm" isHorizontal>
|
||||
<FormGroup
|
||||
hasNoPaddingTop
|
||||
|
|
|
@ -7,6 +7,8 @@
|
|||
"providers": "Add providers",
|
||||
"addKerberos": "Add Kerberos providers",
|
||||
"addLdap": "Add LDAP providers",
|
||||
"addKerberosWizardTitle": "Add Kerberos user federation provider",
|
||||
"addLdapWizardTitle": "Add LDAP user federation provider",
|
||||
|
||||
"syncChangedUsers": "Sync changed users",
|
||||
"syncAllUsers": "Sync all users",
|
||||
|
|
Loading…
Reference in a new issue