Migrate TermsDialog to TypeScript

pull/21833/head
Germain Souquet 2021-06-14 23:50:41 +01:00
parent de414cd0a6
commit 75151b7a6c
1 changed files with 53 additions and 47 deletions

View File

@ -16,22 +16,21 @@ limitations under the License.
import url from 'url'; import url from 'url';
import React from 'react'; import React from 'react';
import PropTypes from 'prop-types';
import * as sdk from '../../../index'; import * as sdk from '../../../index';
import { _t, pickBestLanguage } from '../../../languageHandler'; import { _t, pickBestLanguage } from '../../../languageHandler';
import {replaceableComponent} from "../../../utils/replaceableComponent"; import {replaceableComponent} from "../../../utils/replaceableComponent";
import {SERVICE_TYPES} from "matrix-js-sdk/src/service-types"; import { SERVICE_TYPES } from "matrix-js-sdk/src/service-types";
class TermsCheckbox extends React.PureComponent { interface ITermsCheckboxProps {
static propTypes = { onChange: (url: string, checked: boolean) => void;
onChange: PropTypes.func.isRequired, url: string;
url: PropTypes.string.isRequired, checked: boolean;
checked: PropTypes.bool.isRequired, }
}
onChange = (ev) => { class TermsCheckbox extends React.PureComponent<ITermsCheckboxProps> {
this.props.onChange(this.props.url, ev.target.checked); private onChange = (ev: React.FormEvent<HTMLInputElement>): void => {
this.props.onChange(this.props.url, ev.currentTarget.checked);
} }
render() { render() {
@ -42,30 +41,34 @@ class TermsCheckbox extends React.PureComponent {
} }
} }
interface ITermsDialogProps {
/**
* Array of [Service, policies] pairs, where policies is the response from the
* /terms endpoint for that service
*/
policiesAndServicePairs: any[],
/**
* urls that the user has already agreed to
*/
agreedUrls?: string[],
/**
* Called with:
* * success {bool} True if the user accepted any douments, false if cancelled
* * agreedUrls {string[]} List of agreed URLs
*/
onFinished: (success: boolean, agreedUrls?: string[]) => void,
}
interface IState {
agreedUrls: any;
}
@replaceableComponent("views.dialogs.TermsDialog") @replaceableComponent("views.dialogs.TermsDialog")
export default class TermsDialog extends React.PureComponent { export default class TermsDialog extends React.PureComponent<ITermsDialogProps, IState> {
static propTypes = {
/**
* Array of [Service, policies] pairs, where policies is the response from the
* /terms endpoint for that service
*/
policiesAndServicePairs: PropTypes.array.isRequired,
/**
* urls that the user has already agreed to
*/
agreedUrls: PropTypes.arrayOf(PropTypes.string),
/**
* Called with:
* * success {bool} True if the user accepted any douments, false if cancelled
* * agreedUrls {string[]} List of agreed URLs
*/
onFinished: PropTypes.func.isRequired,
}
constructor(props) { constructor(props) {
super(); super(props);
this.state = { this.state = {
// url -> boolean // url -> boolean
agreedUrls: {}, agreedUrls: {},
@ -75,15 +78,15 @@ export default class TermsDialog extends React.PureComponent {
} }
} }
_onCancelClick = () => { private onCancelClick = (): void => {
this.props.onFinished(false); this.props.onFinished(false);
} }
_onNextClick = () => { private onNextClick = (): void => {
this.props.onFinished(true, Object.keys(this.state.agreedUrls).filter((url) => this.state.agreedUrls[url])); this.props.onFinished(true, Object.keys(this.state.agreedUrls).filter((url) => this.state.agreedUrls[url]));
} }
_nameForServiceType(serviceType, host) { private nameForServiceType(serviceType: SERVICE_TYPES, host: string): JSX.Element {
switch (serviceType) { switch (serviceType) {
case SERVICE_TYPES.IS: case SERVICE_TYPES.IS:
return <div>{_t("Identity Server")}<br />({host})</div>; return <div>{_t("Identity Server")}<br />({host})</div>;
@ -92,7 +95,7 @@ export default class TermsDialog extends React.PureComponent {
} }
} }
_summaryForServiceType(serviceType) { private summaryForServiceType(serviceType: SERVICE_TYPES): JSX.Element {
switch (serviceType) { switch (serviceType) {
case SERVICE_TYPES.IS: case SERVICE_TYPES.IS:
return <div> return <div>
@ -107,13 +110,13 @@ export default class TermsDialog extends React.PureComponent {
} }
} }
_onTermsCheckboxChange = (url, checked) => { private onTermsCheckboxChange = (url: string, checked: boolean) => {
this.setState({ this.setState({
agreedUrls: Object.assign({}, this.state.agreedUrls, { [url]: checked }), agreedUrls: Object.assign({}, this.state.agreedUrls, { [url]: checked }),
}); });
} }
render() { public render() {
const BaseDialog = sdk.getComponent('views.dialogs.BaseDialog'); const BaseDialog = sdk.getComponent('views.dialogs.BaseDialog');
const DialogButtons = sdk.getComponent('views.elements.DialogButtons'); const DialogButtons = sdk.getComponent('views.elements.DialogButtons');
@ -128,8 +131,8 @@ export default class TermsDialog extends React.PureComponent {
let serviceName; let serviceName;
let summary; let summary;
if (i === 0) { if (i === 0) {
serviceName = this._nameForServiceType(policiesAndService.service.serviceType, parsedBaseUrl.host); serviceName = this.nameForServiceType(policiesAndService.service.serviceType, parsedBaseUrl.host);
summary = this._summaryForServiceType( summary = this.summaryForServiceType(
policiesAndService.service.serviceType, policiesAndService.service.serviceType,
); );
} }
@ -137,12 +140,15 @@ export default class TermsDialog extends React.PureComponent {
rows.push(<tr key={termDoc[termsLang].url}> rows.push(<tr key={termDoc[termsLang].url}>
<td className="mx_TermsDialog_service">{serviceName}</td> <td className="mx_TermsDialog_service">{serviceName}</td>
<td className="mx_TermsDialog_summary">{summary}</td> <td className="mx_TermsDialog_summary">{summary}</td>
<td>{termDoc[termsLang].name} <a rel="noreferrer noopener" target="_blank" href={termDoc[termsLang].url}> <td>
<span className="mx_TermsDialog_link" /> {termDoc[termsLang].name}
</a></td> <a rel="noreferrer noopener" target="_blank" href={termDoc[termsLang].url}>
<span className="mx_TermsDialog_link" />
</a>
</td>
<td><TermsCheckbox <td><TermsCheckbox
url={termDoc[termsLang].url} url={termDoc[termsLang].url}
onChange={this._onTermsCheckboxChange} onChange={this.onTermsCheckboxChange}
checked={Boolean(this.state.agreedUrls[termDoc[termsLang].url])} checked={Boolean(this.state.agreedUrls[termDoc[termsLang].url])}
/></td> /></td>
</tr>); </tr>);
@ -176,7 +182,7 @@ export default class TermsDialog extends React.PureComponent {
return ( return (
<BaseDialog <BaseDialog
fixedWidth={false} fixedWidth={false}
onFinished={this._onCancelClick} onFinished={this.onCancelClick}
title={_t("Terms of Service")} title={_t("Terms of Service")}
contentId='mx_Dialog_content' contentId='mx_Dialog_content'
hasCancel={false} hasCancel={false}
@ -197,8 +203,8 @@ export default class TermsDialog extends React.PureComponent {
<DialogButtons primaryButton={_t('Next')} <DialogButtons primaryButton={_t('Next')}
hasCancel={true} hasCancel={true}
onCancel={this._onCancelClick} onCancel={this.onCancelClick}
onPrimaryButtonClick={this._onNextClick} onPrimaryButtonClick={this.onNextClick}
primaryDisabled={!enableSubmit} primaryDisabled={!enableSubmit}
/> />
</BaseDialog> </BaseDialog>