Skip to content

Commit

Permalink
Initial UI work
Browse files Browse the repository at this point in the history
Signed-off-by: Taylor Smock <tsmock@meta.com>
  • Loading branch information
tsmock committed Apr 17, 2024
1 parent 5e8e418 commit c4c235e
Show file tree
Hide file tree
Showing 6 changed files with 94 additions and 14 deletions.
41 changes: 36 additions & 5 deletions frontend/src/components/deleteModal/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,34 @@ import { DeleteButton } from '../teamsAndOrgs/management';
import { Button } from '../button';
import { AlertIcon } from '../svgIcons';

export function DeleteModal({ id, name, type, className, endpointURL, onDelete }: Object) {
/**
* Called when an object is deleted
* @callback onDelete
* @param success The success object
*/

/**
* Create a delete modal
* @param {number} [id] The id of the object to delete. Ignored if className is defined.
* @param {str} [name] The name of the object (unused)
* @param {('notifications'|'comments'|'users'|'interests'|'categories')} [type] The type of the object to delete. Ignored if className is defined.
* @param {str} [className] The additional css class names
* @param {str} [endpointURL] The endpoint to call
* @param {onDelete} [onDelete] Called when the object is deleted
* @typedef {import('@formatjs/intl').MessageDescriptor} MessageDescriptor
* @param {MessageDescriptor} [message] The message to show the user
* @returns {Element} The delete modal
* @constructor
*/
export function DeleteModal({
id,
name,
type,
className,
endpointURL,
onDelete,
message = messages.delete,
}: Object) {
const navigate = useNavigate();
const modalRef = useRef();
const token = useSelector((state) => state.auth.token);
Expand All @@ -26,9 +53,9 @@ export function DeleteModal({ id, name, type, className, endpointURL, onDelete }
setDeleteStatus('success');
if (type === 'notifications') {
setTimeout(() => navigate(`/inbox`), 750);
} else if (type === 'comments') {
} else if (type === 'comments' || type === 'users') {
setTimeout(() => {
onDelete();
onDelete(success);
modalRef.current.close();
}, 750);
return;
Expand All @@ -46,7 +73,11 @@ export function DeleteModal({ id, name, type, className, endpointURL, onDelete }
<Popup
ref={modalRef}
trigger={
<DeleteButton className={`${className || ''} dib ml3`} showText={type !== 'comments'} />
<DeleteButton
className={`${className || ''} dib ml3`}
showText={type !== 'comments' && type !== 'users'}
message={message}
/>
}
modal
closeOnDocumentClick
Expand Down Expand Up @@ -84,7 +115,7 @@ export function DeleteModal({ id, name, type, className, endpointURL, onDelete }
<FormattedMessage {...messages.cancel} />
</Button>
<Button className="bg-red white" onClick={() => deleteEntity()}>
<FormattedMessage {...messages.delete} />
<FormattedMessage {...message} />
</Button>
</div>
</>
Expand Down
12 changes: 12 additions & 0 deletions frontend/src/components/deleteModal/messages.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,10 @@ export default defineMessages({
id: 'deleteModal.status.success.teams',
defaultMessage: 'Team deleted successfully.',
},
success_users: {
id: 'deleteModal.status.success.users',
defaultMessage: 'User deleted successfully.',
},
success_organisations: {
id: 'deleteModal.status.success.organisations',
defaultMessage: 'Organisation deleted successfully.',
Expand Down Expand Up @@ -68,6 +72,10 @@ export default defineMessages({
id: 'deleteModal.status.failure.teams',
defaultMessage: 'An error occurred when trying to delete this team.',
},
failure_users: {
id: 'deleteModal.status.failure.users',
defaultMessage: 'An error occurred when trying to delete this user.',
},
failure_comments: {
id: 'deleteModal.status.failure.comments',
defaultMessage: 'An error occurred when trying to delete this comment.',
Expand Down Expand Up @@ -117,6 +125,10 @@ export default defineMessages({
id: 'deleteModal.title.teams',
defaultMessage: 'Are you sure you want to delete this team?',
},
confirmDeleteTitle_users: {
id: 'deleteModal.title.users',
defaultMessage: "Are you sure you want to redact this user's information?",
},
confirmDeleteTitle_comments: {
id: 'deleteModal.title.comments',
defaultMessage: 'Are you sure you want to delete this comment?',
Expand Down
21 changes: 18 additions & 3 deletions frontend/src/components/teamsAndOrgs/management.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,15 +24,30 @@ export const AddButton = () => (
</CustomButton>
);

export const DeleteButton = ({ className, onClick, showText = true }: Object) => {
/**
* A button for deleting something
* @param {string} className Additional css classes
* @param {MouseEventHandler<T>} onClick The action to call on click
* @param {boolean} [showText=true] true if the message should be shown
* @typedef {import('@formatjs/intl').MessageDescriptor} MessageDescriptor
* @param {MessageDescriptor} message The message to show
* @returns {Element} The delete button
* @constructor
*/
export const DeleteButton = ({
className,
onClick,
showText = true,
message = messages.delete,
}: Object) => {
const intl = useIntl();
return (
<CustomButton className={`red bg-transparent ba b--red pv1 ${className}`} onClick={onClick}>
<div data-for="Delete" data-tip={!showText ? intl.formatMessage(messages.delete) : ''}>
<div data-for="Delete" data-tip={!showText ? intl.formatMessage(message) : ''}>
<WasteIcon className="v-mid h1 w1" />
{showText && (
<span className="v-mid f4 fw6 ttu barlow-condensed pl2">
<FormattedMessage {...messages.delete} />
<FormattedMessage {...message} />
</span>
)}
</div>
Expand Down
13 changes: 11 additions & 2 deletions frontend/src/components/user/forms/personalInformation.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import React, { useState } from 'react';
import { connect } from 'react-redux';
import { connect, useDispatch } from 'react-redux';
import { Form, Field } from 'react-final-form';
import ReactTooltip from 'react-tooltip';
import { FormattedMessage, useIntl } from 'react-intl';
Expand All @@ -8,9 +8,10 @@ import messages from '../messages';
import { FormSubmitButton } from '../../button';
import { InfoIcon, CheckIcon, CloseIcon } from '../../svgIcons';
import { UserCountrySelect, RadioField } from '../../formInputs';
import { pushUserDetails } from '../../../store/actions/auth';
import { logout, pushUserDetails } from '../../../store/actions/auth';
import { fetchLocalJSONAPI } from '../../../network/genericJSONRequest';
import { ORG_CODE } from '../../../config';
import { DeleteModal } from '../../deleteModal';

export const PROFILE_RELEVANT_FIELDS = [
'name',
Expand Down Expand Up @@ -75,6 +76,7 @@ const RequiredIndicator = () => <span className="ml1 b red">*</span>;

function _PersonalInformationForm({ userDetails, token, pushUserDetails }) {
const intl = useIntl();
const dispatch = useDispatch();
const labelClasses = 'db pt3 pb2';
const fieldClasses =
'blue-dark w-100 pv2 ph2 input-reset ba br1 b--grey-light bg-transparent lh-copy';
Expand Down Expand Up @@ -255,6 +257,13 @@ function _PersonalInformationForm({ userDetails, token, pushUserDetails }) {
>
<FormattedMessage {...messages.save} />
</FormSubmitButton>
<DeleteModal
id={userDetails.id}
name={userDetails.username}
className="bg-transparent bw0 w2 h2 lh-copy overflow-hidden blue-light p0 mb1 hover-red"
type="users"
onDelete={() => dispatch(logout())}
/>
</div>
<p className="f6 mt2 tr mb0">
<RequiredIndicator /> <FormattedMessage {...messages.required} />
Expand Down
17 changes: 13 additions & 4 deletions frontend/src/components/user/list.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import { PaginatorLine } from '../paginator';
import { SearchIcon, CloseIcon, SettingsIcon, CheckIcon } from '../svgIcons';
import { Dropdown } from '../dropdown';
import { nCardPlaceholders } from './usersPlaceholder';
import { DeleteModal } from '../deleteModal';

const UserFilter = ({ filters, setFilters, updateFilters, intl }) => {
const inputRef = useRef(null);
Expand Down Expand Up @@ -289,7 +290,7 @@ export const UserEditMenu = ({ user, token, close, setStatus }) => {
);
})}
</div>
<div className="w-100">
<div className="w-100 bb b--tan">
<p className="b mv3">
<FormattedMessage {...messages.setLevel} />
</p>
Expand All @@ -315,6 +316,7 @@ export const UserEditMenu = ({ user, token, close, setStatus }) => {

export function UserListCard({ user, token, username, setStatus }: Object) {
const [isHovered, setHovered] = useState(false);
const [other_username, setUserName] = useState(user.username);

return (
<li
Expand All @@ -328,16 +330,16 @@ export function UserListCard({ user, token, username, setStatus }: Object) {
<div className="w-50-ns w-100 fl">
<UserAvatar
picture={user.pictureUrl}
username={user.username}
username={other_username}
colorClasses="white bg-blue-grey"
/>
<a
className="blue-grey mr2 ml3 link"
rel="noopener noreferrer"
target="_blank"
href={`/users/${user.username}`}
href={`/users/${other_username}`}
>
{user.username}
{other_username}
</a>
</div>
<div className="w-20 fl dib-ns dn tc">
Expand All @@ -363,6 +365,13 @@ export function UserListCard({ user, token, username, setStatus }: Object) {
<UserEditMenu user={user} token={token} close={close} setStatus={setStatus} />
)}
</Popup>
<DeleteModal
id={user.id}
name={user.username}
type="users"
className="bg-transparent bw0 w2 h2 lh-copy overflow-hidden blue-light p0 mb1 hover-red"
onDelete={() => setUserName('user_' + user.id)}
/>
</div>
)}
</li>
Expand Down
4 changes: 4 additions & 0 deletions frontend/src/components/user/messages.js
Original file line number Diff line number Diff line change
Expand Up @@ -334,6 +334,10 @@ export default defineMessages({
id: 'users.list.actions.setLevel',
defaultMessage: 'Set mapper level',
},
redactUser: {
id: 'users.list.actions.redact',
defaultMessage: 'Redact user information',
},
userAttributeUpdationSuccess: {
id: 'users.list.attribute.updation.success',
defaultMessage:
Expand Down

0 comments on commit c4c235e

Please sign in to comment.