diff options
author | Eugen Rochko <eugen@zeonfederated.com> | 2022-01-17 09:41:33 +0100 |
---|---|---|
committer | Claire <claire.github-309c@sitedethib.com> | 2022-01-17 11:19:44 +0100 |
commit | 69208ef6ff16860a885eb389b3d14afd93531252 (patch) | |
tree | 1f3e618af62a8c9cc13c98abe77497785d93015c /app/javascript/flavours/glitch/components/admin | |
parent | b3bf32a21e4dfc43737f50f15d3f258c16d0cf83 (diff) |
[Glitch] Add notifications for statuses deleted by moderators
Port front-end changes from 14f436c457560862fafabd753eb314c8b8a8e674 to glitch-soc Signed-off-by: Claire <claire.github-309c@sitedethib.com>
Diffstat (limited to 'app/javascript/flavours/glitch/components/admin')
-rw-r--r-- | app/javascript/flavours/glitch/components/admin/ReportReasonSelector.js | 159 |
1 files changed, 159 insertions, 0 deletions
diff --git a/app/javascript/flavours/glitch/components/admin/ReportReasonSelector.js b/app/javascript/flavours/glitch/components/admin/ReportReasonSelector.js new file mode 100644 index 000000000..0f2a4fe36 --- /dev/null +++ b/app/javascript/flavours/glitch/components/admin/ReportReasonSelector.js @@ -0,0 +1,159 @@ +import React from 'react'; +import PropTypes from 'prop-types'; +import api from 'flavours/glitch/util/api'; +import { injectIntl, defineMessages } from 'react-intl'; +import classNames from 'classnames'; + +const messages = defineMessages({ + other: { id: 'report.categories.other', defaultMessage: 'Other' }, + spam: { id: 'report.categories.spam', defaultMessage: 'Spam' }, + violation: { id: 'report.categories.violation', defaultMessage: 'Content violates one or more server rules' }, +}); + +class Category extends React.PureComponent { + + static propTypes = { + id: PropTypes.string.isRequired, + text: PropTypes.string.isRequired, + selected: PropTypes.bool, + disabled: PropTypes.bool, + onSelect: PropTypes.func, + children: PropTypes.node, + }; + + handleClick = () => { + const { id, disabled, onSelect } = this.props; + + if (!disabled) { + onSelect(id); + } + }; + + render () { + const { id, text, disabled, selected, children } = this.props; + + return ( + <div tabIndex='0' role='button' className={classNames('report-reason-selector__category', { selected, disabled })} onClick={this.handleClick}> + {selected && <input type='hidden' name='report[category]' value={id} />} + + <div className='report-reason-selector__category__label'> + <span className={classNames('poll__input', { active: selected, disabled })} /> + {text} + </div> + + {(selected && children) && ( + <div className='report-reason-selector__category__rules'> + {children} + </div> + )} + </div> + ); + } + +} + +class Rule extends React.PureComponent { + + static propTypes = { + id: PropTypes.string.isRequired, + text: PropTypes.string.isRequired, + selected: PropTypes.bool, + disabled: PropTypes.bool, + onToggle: PropTypes.func, + }; + + handleClick = () => { + const { id, disabled, onToggle } = this.props; + + if (!disabled) { + onToggle(id); + } + }; + + render () { + const { id, text, disabled, selected } = this.props; + + return ( + <div tabIndex='0' role='button' className={classNames('report-reason-selector__rule', { selected, disabled })} onClick={this.handleClick}> + <span className={classNames('poll__input', { checkbox: true, active: selected, disabled })} /> + {selected && <input type='hidden' name='report[rule_ids][]' value={id} />} + {text} + </div> + ); + } + +} + +export default @injectIntl +class ReportReasonSelector extends React.PureComponent { + + static propTypes = { + id: PropTypes.string.isRequired, + category: PropTypes.string.isRequired, + rule_ids: PropTypes.arrayOf(PropTypes.string), + disabled: PropTypes.bool, + intl: PropTypes.object.isRequired, + }; + + state = { + category: this.props.category, + rule_ids: this.props.rule_ids || [], + rules: [], + }; + + componentDidMount() { + api().get('/api/v1/instance').then(res => { + this.setState({ + rules: res.data.rules, + }); + }).catch(err => { + console.error(err); + }); + } + + _save = () => { + const { id, disabled } = this.props; + const { category, rule_ids } = this.state; + + if (disabled) { + return; + } + + api().put(`/api/v1/admin/reports/${id}`, { + category, + rule_ids, + }).catch(err => { + console.error(err); + }); + }; + + handleSelect = id => { + this.setState({ category: id }, () => this._save()); + }; + + handleToggle = id => { + const { rule_ids } = this.state; + + if (rule_ids.includes(id)) { + this.setState({ rule_ids: rule_ids.filter(x => x !== id ) }, () => this._save()); + } else { + this.setState({ rule_ids: [...rule_ids, id] }, () => this._save()); + } + }; + + render () { + const { disabled, intl } = this.props; + const { rules, category, rule_ids } = this.state; + + return ( + <div className='report-reason-selector'> + <Category id='other' text={intl.formatMessage(messages.other)} selected={category === 'other'} onSelect={this.handleSelect} disabled={disabled} /> + <Category id='spam' text={intl.formatMessage(messages.spam)} selected={category === 'spam'} onSelect={this.handleSelect} disabled={disabled} /> + <Category id='violation' text={intl.formatMessage(messages.violation)} selected={category === 'violation'} onSelect={this.handleSelect} disabled={disabled}> + {rules.map(rule => <Rule key={rule.id} id={rule.id} text={rule.text} selected={rule_ids.includes(rule.id)} onToggle={this.handleToggle} disabled={disabled} />)} + </Category> + </div> + ); + } + +} |