Refactor <DomainBlocks>
to TypeScript (#34347)
Co-authored-by: Claire <claire.github-309c@sitedethib.com>
This commit is contained in:
parent
e2ef173b82
commit
2c70c28bbb
9 changed files with 145 additions and 233 deletions
|
@ -1,85 +0,0 @@
|
|||
import PropTypes from 'prop-types';
|
||||
|
||||
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
|
||||
|
||||
import { Helmet } from 'react-helmet';
|
||||
|
||||
import ImmutablePropTypes from 'react-immutable-proptypes';
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component';
|
||||
import { connect } from 'react-redux';
|
||||
|
||||
import { debounce } from 'lodash';
|
||||
|
||||
import BlockIcon from '@/material-icons/400-24px/block-fill.svg?react';
|
||||
import { Domain } from 'mastodon/components/domain';
|
||||
|
||||
import { fetchDomainBlocks, expandDomainBlocks } from '../../actions/domain_blocks';
|
||||
import { LoadingIndicator } from '../../components/loading_indicator';
|
||||
import ScrollableList from '../../components/scrollable_list';
|
||||
import Column from '../ui/components/column';
|
||||
|
||||
const messages = defineMessages({
|
||||
heading: { id: 'column.domain_blocks', defaultMessage: 'Blocked domains' },
|
||||
});
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
domains: state.getIn(['domain_lists', 'blocks', 'items']),
|
||||
hasMore: !!state.getIn(['domain_lists', 'blocks', 'next']),
|
||||
});
|
||||
|
||||
class Blocks extends ImmutablePureComponent {
|
||||
|
||||
static propTypes = {
|
||||
params: PropTypes.object.isRequired,
|
||||
dispatch: PropTypes.func.isRequired,
|
||||
hasMore: PropTypes.bool,
|
||||
domains: ImmutablePropTypes.orderedSet,
|
||||
intl: PropTypes.object.isRequired,
|
||||
multiColumn: PropTypes.bool,
|
||||
};
|
||||
|
||||
UNSAFE_componentWillMount () {
|
||||
this.props.dispatch(fetchDomainBlocks());
|
||||
}
|
||||
|
||||
handleLoadMore = debounce(() => {
|
||||
this.props.dispatch(expandDomainBlocks());
|
||||
}, 300, { leading: true });
|
||||
|
||||
render () {
|
||||
const { intl, domains, hasMore, multiColumn } = this.props;
|
||||
|
||||
if (!domains) {
|
||||
return (
|
||||
<Column>
|
||||
<LoadingIndicator />
|
||||
</Column>
|
||||
);
|
||||
}
|
||||
|
||||
const emptyMessage = <FormattedMessage id='empty_column.domain_blocks' defaultMessage='There are no blocked domains yet.' />;
|
||||
|
||||
return (
|
||||
<Column bindToDocument={!multiColumn} icon='ban' iconComponent={BlockIcon} heading={intl.formatMessage(messages.heading)} alwaysShowBackButton>
|
||||
<ScrollableList
|
||||
scrollKey='domain_blocks'
|
||||
onLoadMore={this.handleLoadMore}
|
||||
hasMore={hasMore}
|
||||
emptyMessage={emptyMessage}
|
||||
bindToDocument={!multiColumn}
|
||||
>
|
||||
{domains.map(domain =>
|
||||
<Domain key={domain} domain={domain} />,
|
||||
)}
|
||||
</ScrollableList>
|
||||
|
||||
<Helmet>
|
||||
<meta name='robots' content='noindex' />
|
||||
</Helmet>
|
||||
</Column>
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default connect(mapStateToProps)(injectIntl(Blocks));
|
113
app/javascript/mastodon/features/domain_blocks/index.tsx
Normal file
113
app/javascript/mastodon/features/domain_blocks/index.tsx
Normal file
|
@ -0,0 +1,113 @@
|
|||
import { useEffect, useRef, useCallback, useState } from 'react';
|
||||
|
||||
import { defineMessages, useIntl, FormattedMessage } from 'react-intl';
|
||||
|
||||
import { Helmet } from 'react-helmet';
|
||||
|
||||
import BlockIcon from '@/material-icons/400-24px/block-fill.svg?react';
|
||||
import { apiGetDomainBlocks } from 'mastodon/api/domain_blocks';
|
||||
import { Column } from 'mastodon/components/column';
|
||||
import type { ColumnRef } from 'mastodon/components/column';
|
||||
import { ColumnHeader } from 'mastodon/components/column_header';
|
||||
import { Domain } from 'mastodon/components/domain';
|
||||
import ScrollableList from 'mastodon/components/scrollable_list';
|
||||
|
||||
const messages = defineMessages({
|
||||
heading: { id: 'column.domain_blocks', defaultMessage: 'Blocked domains' },
|
||||
});
|
||||
|
||||
const Blocks: React.FC<{ multiColumn: boolean }> = ({ multiColumn }) => {
|
||||
const intl = useIntl();
|
||||
const [domains, setDomains] = useState<string[]>([]);
|
||||
const [loading, setLoading] = useState(false);
|
||||
const [next, setNext] = useState<string | undefined>();
|
||||
const hasMore = !!next;
|
||||
const columnRef = useRef<ColumnRef>(null);
|
||||
|
||||
useEffect(() => {
|
||||
setLoading(true);
|
||||
|
||||
void apiGetDomainBlocks()
|
||||
.then(({ domains, links }) => {
|
||||
const next = links.refs.find((link) => link.rel === 'next');
|
||||
|
||||
setLoading(false);
|
||||
setDomains(domains);
|
||||
setNext(next?.uri);
|
||||
|
||||
return '';
|
||||
})
|
||||
.catch(() => {
|
||||
setLoading(false);
|
||||
});
|
||||
}, [setLoading, setDomains, setNext]);
|
||||
|
||||
const handleLoadMore = useCallback(() => {
|
||||
setLoading(true);
|
||||
|
||||
void apiGetDomainBlocks(next)
|
||||
.then(({ domains, links }) => {
|
||||
const next = links.refs.find((link) => link.rel === 'next');
|
||||
|
||||
setLoading(false);
|
||||
setDomains((previousDomains) => [...previousDomains, ...domains]);
|
||||
setNext(next?.uri);
|
||||
|
||||
return '';
|
||||
})
|
||||
.catch(() => {
|
||||
setLoading(false);
|
||||
});
|
||||
}, [setLoading, setDomains, setNext, next]);
|
||||
|
||||
const handleHeaderClick = useCallback(() => {
|
||||
columnRef.current?.scrollTop();
|
||||
}, []);
|
||||
|
||||
const emptyMessage = (
|
||||
<FormattedMessage
|
||||
id='empty_column.domain_blocks'
|
||||
defaultMessage='There are no blocked domains yet.'
|
||||
/>
|
||||
);
|
||||
|
||||
return (
|
||||
<Column
|
||||
bindToDocument={!multiColumn}
|
||||
ref={columnRef}
|
||||
label={intl.formatMessage(messages.heading)}
|
||||
>
|
||||
<ColumnHeader
|
||||
icon='ban'
|
||||
iconComponent={BlockIcon}
|
||||
title={intl.formatMessage(messages.heading)}
|
||||
onClick={handleHeaderClick}
|
||||
multiColumn={multiColumn}
|
||||
showBackButton
|
||||
/>
|
||||
|
||||
<ScrollableList
|
||||
scrollKey='domain_blocks'
|
||||
onLoadMore={handleLoadMore}
|
||||
hasMore={hasMore}
|
||||
isLoading={loading}
|
||||
showLoading={loading && domains.length === 0}
|
||||
emptyMessage={emptyMessage}
|
||||
trackScroll={!multiColumn}
|
||||
bindToDocument={!multiColumn}
|
||||
>
|
||||
{domains.map((domain) => (
|
||||
<Domain key={domain} domain={domain} />
|
||||
))}
|
||||
</ScrollableList>
|
||||
|
||||
<Helmet>
|
||||
<title>{intl.formatMessage(messages.heading)}</title>
|
||||
<meta name='robots' content='noindex' />
|
||||
</Helmet>
|
||||
</Column>
|
||||
);
|
||||
};
|
||||
|
||||
// eslint-disable-next-line import/no-default-export
|
||||
export default Blocks;
|
Loading…
Add table
Add a link
Reference in a new issue