From f5f96042b33a5456f7be0fc347ef982b1addeea5 Mon Sep 17 00:00:00 2001 From: Sebastian Sdorra Date: Tue, 6 Nov 2018 16:38:49 +0100 Subject: [PATCH] use global configuration abstraction to implement global configuration for git --- scm-plugins/scm-git-plugin/package.json | 2 +- .../src/main/js/GitConfiguration.js | 183 ------------------ .../src/main/js/GitConfigurationForm.js | 79 ++++++++ .../src/main/js/GitConfigurationNavLink.js | 21 -- .../src/main/js/GitConfigurationRoute.js | 25 --- .../src/main/js/GitGlobalConfiguration.js | 32 +++ .../scm-git-plugin/src/main/js/index.js | 12 +- 7 files changed, 116 insertions(+), 238 deletions(-) delete mode 100644 scm-plugins/scm-git-plugin/src/main/js/GitConfiguration.js create mode 100644 scm-plugins/scm-git-plugin/src/main/js/GitConfigurationForm.js delete mode 100644 scm-plugins/scm-git-plugin/src/main/js/GitConfigurationNavLink.js delete mode 100644 scm-plugins/scm-git-plugin/src/main/js/GitConfigurationRoute.js create mode 100644 scm-plugins/scm-git-plugin/src/main/js/GitGlobalConfiguration.js diff --git a/scm-plugins/scm-git-plugin/package.json b/scm-plugins/scm-git-plugin/package.json index 2774af8b26..f295924923 100644 --- a/scm-plugins/scm-git-plugin/package.json +++ b/scm-plugins/scm-git-plugin/package.json @@ -1,6 +1,6 @@ { "name": "@scm-manager/scm-git-plugin", - "license" : "BSD-3-Clause", + "license": "BSD-3-Clause", "main": "src/main/js/index.js", "scripts": { "build": "ui-bundler plugin", diff --git a/scm-plugins/scm-git-plugin/src/main/js/GitConfiguration.js b/scm-plugins/scm-git-plugin/src/main/js/GitConfiguration.js deleted file mode 100644 index d886256d32..0000000000 --- a/scm-plugins/scm-git-plugin/src/main/js/GitConfiguration.js +++ /dev/null @@ -1,183 +0,0 @@ -//@flow -import React from "react"; -import { translate } from "react-i18next"; -import type { Links } from "@scm-manager/ui-types"; -import { - apiClient, - Title, - InputField, - Checkbox, - SubmitButton, - Loading, - ErrorNotification -} from "@scm-manager/ui-components"; - -type Props = { - url: string, - - // context props - t: (string) => string -}; - -type Configuration = { - repositoryDirectory?: string, - gcExpression?: string, - disabled: boolean, - _links?: Links -} - -type State = Configuration & { - error?: Error, - fetching: boolean, - modifying: boolean -}; - -class GitConfiguration extends React.Component { - - constructor(props: Props) { - super(props); - this.state = { - disabled: false, - fetching: true, - modifying: false - }; - } - - componentDidMount() { - const { url } = this.props; - - // TODO capture content-type for sending - - apiClient.get(url) - .then(response => response.json()) - .then(this.loadConfig) - .catch(this.handleError); - } - - handleError = (error: Error) => { - this.setState({ - error, - fetching: false, - modifying: false - }); - }; - - loadConfig = (configuration: Configuration) => { - this.setState({ - ...configuration, - fetching: false, - error: undefined - }); - }; - - handleInputChange = (value: string, name: string) => { - this.setState({ - [name]: value - }); - }; - - handleCheckboxChange = (value: boolean, name: string) => { - this.setState({ - [name]: value - }); - }; - - isValid = (): boolean => { - const { repositoryDirectory } = this.state; - return !!repositoryDirectory; - }; - - getModificationUrl = (): ?string => { - const links = this.state._links; - if (links && links.update) { - return links.update.href; - } - }; - - isReadOnly = (): boolean => { - const links = this.state._links; - return !links || !links.update; - }; - - render() { - const { fetching, error } = this.state; - - if (error) { - return this.renderWithFrame(); - } else if (fetching) { - return this.renderWithFrame(); - } - - return this.renderForm(); - } - - renderWithFrame(child) { - const { t } = this.props; - return ( -
- - {child} - </div> - ); - } - - modifyConfiguration = (event: Event) => { - event.preventDefault(); - - this.setState({ modifying: true }); - - const { repositoryDirectory, gcExpression, disabled } = this.state; - - const configuration = { - repositoryDirectory, - gcExpression, - disabled - }; - - apiClient.put(this.getModificationUrl(), configuration, "application/vnd.scmm-gitconfig+json;v=2") - .then(() => this.setState({ modifying: false })) - .catch(this.handleError); - }; - - renderForm() { - const { repositoryDirectory, gcExpression, disabled, modifying } = this.state; - - const { t } = this.props; - const readOnly = this.isReadOnly(); - - return this.renderWithFrame( - <form onSubmit={this.modifyConfiguration}> - <InputField name="repositoryDirectory" - label={t("scm-git-plugin.config.directory")} - helpText={t("scm-git-plugin.config.directoryHelpText")} - value={repositoryDirectory} - onChange={this.handleInputChange} - disabled={readOnly} - /> - <InputField name="gcExpression" - label={t("scm-git-plugin.config.gcExpression")} - helpText={t("scm-git-plugin.config.gcExpressionHelpText")} - value={gcExpression} - onChange={this.handleInputChange} - disabled={readOnly} - /> - <Checkbox name="disabled" - label={t("scm-git-plugin.config.disabled")} - helpText={t("scm-git-plugin.config.disabledHelpText")} - checked={disabled} - onChange={this.handleCheckboxChange} - disabled={readOnly} - /> - <hr/> - <SubmitButton - label={t("scm-git-plugin.config.submit")} - disabled={!this.isValid() || readOnly} - loading={modifying} - /> - </form> - ); - } - -} - -export default translate("plugins")(GitConfiguration); diff --git a/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationForm.js b/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationForm.js new file mode 100644 index 0000000000..630984ad87 --- /dev/null +++ b/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationForm.js @@ -0,0 +1,79 @@ +//@flow +import React from "react"; +import { translate } from "react-i18next"; +import type { Links } from "@scm-manager/ui-types"; + +import { InputField, Checkbox } from "@scm-manager/ui-components"; + +type Configuration = { + repositoryDirectory?: string, + gcExpression?: string, + disabled: boolean, + _links: Links +} + +type Props = { + initialConfiguration: Configuration, + readOnly: boolean, + + onConfigurationChange: (Configuration, boolean) => void, + + // context props + t: (string) => string +} + +type State = Configuration & { + +} + +class GitConfigurationForm extends React.Component<Props, State> { + + constructor(props: Props) { + super(props); + this.state = { ...props.initialConfiguration }; + } + + isValid = () => { + return !!this.state.repositoryDirectory; + }; + + handleChange = (value: any, name: string) => { + this.setState({ + [name]: value + }, () => this.props.onConfigurationChange(this.state, this.isValid())); + }; + + render() { + const { repositoryDirectory, gcExpression, disabled } = this.state; + const { readOnly, t } = this.props; + + return ( + <> + <InputField name="repositoryDirectory" + label={t("scm-git-plugin.config.directory")} + helpText={t("scm-git-plugin.config.directoryHelpText")} + value={repositoryDirectory} + onChange={this.handleChange} + disabled={readOnly} + /> + <InputField name="gcExpression" + label={t("scm-git-plugin.config.gcExpression")} + helpText={t("scm-git-plugin.config.gcExpressionHelpText")} + value={gcExpression} + onChange={this.handleChange} + disabled={readOnly} + /> + <Checkbox name="disabled" + label={t("scm-git-plugin.config.disabled")} + helpText={t("scm-git-plugin.config.disabledHelpText")} + checked={disabled} + onChange={this.handleChange} + disabled={readOnly} + /> + </> + ); + } + +} + +export default translate("plugins")(GitConfigurationForm); diff --git a/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationNavLink.js b/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationNavLink.js deleted file mode 100644 index 5c8375bc25..0000000000 --- a/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationNavLink.js +++ /dev/null @@ -1,21 +0,0 @@ -//@flow -import React from "react"; -import { NavLink } from "@scm-manager/ui-components"; -import { translate } from "react-i18next"; - -type Props = { - url: string, - - // context props - t: (string) => string -} -class GitConfigurationNavLink extends React.Component<Props> { - - render() { - const { url, t } = this.props; - return <NavLink to={`${url}/git`} label={t("scm-git-plugin.config.link")} />; - } - -} - -export default translate("plugins")(GitConfigurationNavLink); diff --git a/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationRoute.js b/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationRoute.js deleted file mode 100644 index 3d183e3ee9..0000000000 --- a/scm-plugins/scm-git-plugin/src/main/js/GitConfigurationRoute.js +++ /dev/null @@ -1,25 +0,0 @@ -//@flow -import React from "react"; -import type { Links } from "@scm-manager/ui-types"; -import GitConfiguration from "./GitConfiguration"; -import { Route } from "react-router-dom"; - -type Props = { - url: string, - links: Links -} - -class GitConfigurationRoute extends React.Component<Props> { - - render() { - const { url, links } = this.props; - - const configLink = links["gitConfig"].href; - return <Route path={url + "/git"} - component={() => <GitConfiguration url={configLink} />} - exact />; - } - -} - -export default GitConfigurationRoute; diff --git a/scm-plugins/scm-git-plugin/src/main/js/GitGlobalConfiguration.js b/scm-plugins/scm-git-plugin/src/main/js/GitGlobalConfiguration.js new file mode 100644 index 0000000000..3718cc2900 --- /dev/null +++ b/scm-plugins/scm-git-plugin/src/main/js/GitGlobalConfiguration.js @@ -0,0 +1,32 @@ +//@flow +import React from "react"; +import { translate } from "react-i18next"; +import { Title, GlobalConfiguration } from "@scm-manager/ui-components"; +import GitConfigurationForm from "./GitConfigurationForm"; + +type Props = { + link: string, + + t: (string) => string +}; + +class GitGlobalConfiguration extends React.Component<Props> { + + constructor(props: Props) { + super(props); + } + + render() { + const { link, t } = this.props; + + return ( + <div> + <Title title={t("scm-git-plugin.config.title")}/> + <GlobalConfiguration link={link} render={props => <GitConfigurationForm {...props} />}/> + </div> + ); + } + +} + +export default translate("plugins")(GitGlobalConfiguration); diff --git a/scm-plugins/scm-git-plugin/src/main/js/index.js b/scm-plugins/scm-git-plugin/src/main/js/index.js index 815f016b88..3f91405509 100644 --- a/scm-plugins/scm-git-plugin/src/main/js/index.js +++ b/scm-plugins/scm-git-plugin/src/main/js/index.js @@ -2,8 +2,9 @@ import { binder } from "@scm-manager/ui-extensions"; import ProtocolInformation from "./ProtocolInformation"; import GitAvatar from "./GitAvatar"; -import GitConfigurationNavLink from "./GitConfigurationNavLink"; -import GitConfigurationRoute from "./GitConfigurationRoute"; + +import { ConfigurationBinder as cfgBinder } from "@scm-manager/ui-components"; +import GitGlobalConfiguration from "./GitGlobalConfiguration"; // repository @@ -16,9 +17,4 @@ binder.bind("repos.repository-avatar", GitAvatar, gitPredicate); // global config -const gitConfigPredicate = (props: Object) => { - return props.links && props.links["gitConfig"]; -}; - -binder.bind("config.navigation", GitConfigurationNavLink, gitConfigPredicate); -binder.bind("config.route", GitConfigurationRoute, gitConfigPredicate); +cfgBinder.bindGlobal("/git", "scm-git-plugin.config.link", "gitConfig", GitGlobalConfiguration);